<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 - Register allocator spills although free registers are available"
   href="https://bugs.llvm.org/show_bug.cgi?id=37073">37073</a>
          </td>
        </tr>

        <tr>
          <th>Summary</th>
          <td>Register allocator spills although free registers are available
          </td>
        </tr>

        <tr>
          <th>Product</th>
          <td>new-bugs
          </td>
        </tr>

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

        <tr>
          <th>Hardware</th>
          <td>Other
          </td>
        </tr>

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

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

        <tr>
          <th>Severity</th>
          <td>enhancement
          </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>gergo.barany@inria.fr
          </td>
        </tr>

        <tr>
          <th>CC</th>
          <td>llvm-bugs@lists.llvm.org
          </td>
        </tr></table>
      <p>
        <div>
        <pre>Created <span class=""><a href="attachment.cgi?id=20180" name="attach_20180" title="input program">attachment 20180</a> <a href="attachment.cgi?id=20180&action=edit" title="input program">[details]</a></span>
input program

The attached test file contains a simple function doing elementary arithmetic,
using only local double variables, without any branching:

double fn1(double p1, double p2, double p3, double p4, double p5, double p6,
           double p7, double p8) {
  double a, b, c, d, v, e;
  a = p4 - 5 + 9 * p1 * 7;
  c = 2 - p6 + 1;
  b = 3 * p6 * 4 - (p2 + 10) * a;
  d = (8 + p3) * p5 * 5 * p7 - p4;
  v = p1 - p8 - 2 - (p8 + p2 - b) * ((p3 + 6) * c);
  e = v * p5 + d; 
  return e;


Compiling it for ARMv7-A with VFPv3-D16 floating-point support generates the
following code snippet (comments mine):

    ...
    vmov.f64    d13, #4.000000e+00      @ def d13
    vmov.f64    d14, #1.000000e+01      @ def d14
    vmul.f64    d10, d10, d13           @ last use of d13
    vadd.f64    d11, d1, d14            @ last use of d14
    vmov.f64    d12, #2.000000e+00
    vmov.f64    d15, #8.000000e+00      @ def d15
    vsub.f64    d5, d12, d5
    vadd.f64    d12, d2, d15            @ last use of d15
    vmls.f64    d10, d11, d9
    vstr    d6, [sp]                    @ spill original value of d6
    vmov.f64    d6, #6.000000e+00       @ use d6 for constant 6.0
    ...

That is, at some point the constant 6.0 must be loaded into a register, and the
default allocator decides to spill d6 to accommodate this value. But just above
this code three other registers are briefly used and never touched again: d13,
d14, and d15 would all be available to accommodate the constant without causing
a spill.

(GCC doesn't have this inline spill, and it saves fewer callee-saved registers
because it does more register reuse.)

Online: <a href="https://godbolt.org/g/8ZuYbz">https://godbolt.org/g/8ZuYbz</a> (note: the link shows the behavior of
Clang 6.0.0, but it's the same on trunk)

Flags: --target=armv7a-eabihf -march=armv7-a -mfpu=vfpv3-d16 -mfloat-abi=hard
-O3 -fomit-frame-pointer

Version: LLVM r328450, Clang r328447 from 2018-03-25</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>