<table border="1" cellspacing="0" cellpadding="8">
    <tr>
        <th>Issue</th>
        <td>
            <a href=https://github.com/llvm/llvm-project/issues/86949>86949</a>
        </td>
    </tr>

    <tr>
        <th>Summary</th>
        <td>
            Missed optimization (inline breaks knowledge about [[pure]])
        </td>
    </tr>

    <tr>
      <th>Labels</th>
      <td>
            new issue
      </td>
    </tr>

    <tr>
      <th>Assignees</th>
      <td>
      </td>
    </tr>

    <tr>
      <th>Reporter</th>
      <td>
          kelbon
      </td>
    </tr>
</table>

<pre>
    
This code (intuitively) seams easy to optimize: function 'sum_foo' is pure, it does not change its arguments, so its result will be always same. Expected calculate one time + multiply by 100'000

But looks like compiler inlines 'sum_foo' and forgets, that it is [[pure]]. Then it tries to do all smart things about loops, but do not understands, that loop does not change its body
So, i added [[gnu::noinline]] and both gcc and clang create 100'000 * sum_foo, as expected.

```asm
foo(int*, int):                              # @foo(int*, int)
        push    rax
        call    sum_foo(int const*, int)
        imul    rax, rax, 100000
        pop     rcx
 ret
```

I think it is very confusing behavior and may be fixed

```cpp
[[gnu::pure]] [[gnu::noinline]] static long long sum_foo(const int* data, int arraySize) noexcept {
    long long sum = 0;
    for (int c = 0; c < arraySize; ++c)
        sum += data[c];
 return sum;
}
long long foo(int* data, int arraySize) noexcept {
 long long sum = 0;
   for (int i = 0; i < 100000; ++i)
       sum += sum_foo(data, arraySize);
   return sum;
}

```
https://godbolt.org/z/53Y8P34dx

</pre>
<img width="1px" height="1px" alt="" src="http://email.email.llvm.org/o/eJyUVUuPozgX_TXO5qojMCGEBYuk8kX6FiON1L2Z1cjYF_DE2MiPqkr_-pENeVSmploTRdj4ce855x5j5pzsNWJDygMpjysW_GBsc0bVGr1qjbg0JDuSbP9jkA64EQiE7qT2QXr5iupCaA0O2egAmbuAN2AmL0f5E0mxhy5o7qXRQGjlwvhnZwyhFUgHU7BI6AtID8KgA2088IHpHkF6B8z2YUTtXVzjTBqz6ILy8CaVghaBqTd2ceDYiGv43_uE3KMAzhQPinkEoxG8HCPgA4xBeTmpC7QXyLOM0CrLspnZ_DwED8qYswMlzwjcjJNUaEFqJTW6JwJMC-iM7XEG6AfmIxPpIOl4SOzKIymPa_gxoI6T3kp0USBhgCkFbmTWgx-k7h2w1swAphSwDVGWJErQAq3zTIt7qrjuU9liwWY-301SF5gQKBZUvQ6k2JNir81Ma4aY2LTGD9Bznl64YroHbjHqeJMLCN3DTYQXYA5wkX39KCXZZvOfuXEeSRuiawjdJ1ixV0eDfPkjtACyyf5ld4p8XToFN8TWsvePEzxKDXDHHQMBN9p9FU6OQV3D0Zdrk2fZzTW3xGZKreXXxBb9kw6P4vw_Vfy8uOUV7SWC6YKTuocWB_YqjU1FGNkl2ryT7yg-lZdP0zLysbp38_2i7s4zLzkoo_v5cRcpCTRLswfBPFuUAmYtu3yPx5vWoA2-c5w8kOpwl-VDPCDFETJSPMx3xsK1Drfp1H15CF8c4sEl9MD_UZ0Ulh7i1gStPPDI6JbDog9Wx2W3MVId584d3KOt_hPFX_B7oCfv9GSitzjoxk0-c3ugdi_GFdwjsMeMX_H91IqD95OLlqAnQk-9Ea1Rfm1sT-jpJ6Gnsvhj93uxEYulV6IpRF3UbIVNXuX5tqBFVa6GhhfdtuYMWVfmot7lxabqaI6YIS0FE91KNjSjm6ygu7yg27xcU5bjdrsrsmqTV1xQsslwZFKtlXodI4KVdC5gs9vWm3qlWIvKpbuJUo1vkCYJpfGqsk3c860NvSObTEnn3T2Kl15h85t0DsX1RmLLTbSbDwG0FtnZwVmbN4Wix-Uj_PwFJ7ReBauaJ9GkH0K75mYk9BTTLs23yZq_kHtCTwmsI_SUyPwdAAD__4bQNIg">