<table border="1" cellspacing="0" cellpadding="8">
<tr>
<th>Issue</th>
<td>
<a href=https://github.com/llvm/llvm-project/issues/62261>62261</a>
</td>
</tr>
<tr>
<th>Summary</th>
<td>
Miscompilation of _BitInt passed as variadic argument
</td>
</tr>
<tr>
<th>Labels</th>
<td>
miscompilation
</td>
</tr>
<tr>
<th>Assignees</th>
<td>
</td>
</tr>
<tr>
<th>Reporter</th>
<td>
ostannard
</td>
</tr>
</table>
<pre>
This code is miscompiled at all optimisation levels except for -O0, and for all (or many) targets (I've tried Arm v7M, AArch64 and x86_64):
```c
#include <stdarg.h>
#include <assert.h>
void F8 (int P0, ...) {
va_list vl;
va_start(vl, P0);
signed _BitInt(13) P1;
P1 = va_arg(vl, signed _BitInt(13));
assert((int)P1 == -42);
}
int main (void) {
F8(0, -42);
return 0;
}
```
Generated code for v7M:
```
$ /work/llvm/build/bin/clang --target=arm-none-eabi -march=armv7-m -c test.c -o - -S -O1
...
F8:
.fnstart
.pad #12
sub sp, #12
.save {r7, lr}
push {r7, lr}
.setfp r7, sp
mov r7, sp
.pad #4
sub sp, #4
add.w r0, r7, #8
stm r0!, {r1, r2, r3}
add.w r0, r7, #8
adds r0, #4
str r0, [sp]
ldrh r0, [r7, #8]
movw r1, #8150
cmp r0, r1
beq .LBB0_2
movw r0, :lower16:.L.str
movw r1, :lower16:.L.str.1
movt r0, :upper16:.L.str
movt r1, :upper16:.L.str.1
movs r2, #10
bl __aeabi_assert
.LBB0_2:
add sp, #4
pop.w {r7, lr}
add sp, #12
bx lr
...
main:
.fnstart
.save {r7, lr}
push {r7, lr}
.setfp r7, sp
mov r7, sp
mvn r1, #41
bl F8
movs r0, #0
pop {r7, pc}
...
```
The draft ABI spec for _BitInt (https://github.com/ARM-software/abi-aa/pull/191/files) says that the non-significant bits are unspecified, but the generated code for F8 compares the 16-bit chunk (loaded with the LDRH instruction) containing the argument and 3 unspecified bits to a constant which has those bits set to zero, which fails because main sign-extended the value into those bits, setting them to 1.
For a non-variadic version of the function, we emit a `BFC` instruction to clear the unspecified bits before comparing them, which is correct:
```c
#include <stdarg.h>
#include <assert.h>
__attribute((noinline))
void F8 (int P0, signed _BitInt(13) P1) {
assert((int)P1 == -42);
}
int main (void) {
F8(0, -42);
return 0;
}
```
```
$ /work/llvm/build/bin/clang --target=arm-none-eabi -march=armv7-m -c test.c -o - -S -O1
...
F8:
.fnstart
bfc r1, #13, #19
movw r0, #8150
cmp r1, r0
it eq
bxeq lr
.LBB0_1:
movw r0, :lower16:.L.str
movw r1, :lower16:.L.str.1
movt r0, :upper16:.L.str
movt r1, :upper16:.L.str.1
movs r2, #7
b __aeabi_assert
...
```
</pre>
<img width="1px" height="1px" alt="" src="http://email.email.llvm.org/o/eJzUV12Tm7gS_TXySxcUCI8_Hvxgz1zuTVVSSeXm3SVEY7QREpEEnuyv35KwPRh7Jtmt3VTt1BRgdHR0ulvqbpi14qAQN-RhRx6eZqxztTYbbR1TiplyVujy--ZLLSxwXSIIC42wXDetkFgCc8CkBN060QjLnNAKJPYoLeAzx9ZBpQ1EHxNCH4GpMvz0MwhdaQMNU98JXYNj5oDO-rfvCF32CM4ILGFrGuiXH_zk7dbwejEPJM-rxX4xJ3RNsi1Jnkhyvi6S4Z-fftNMKC67EoFkj9aVzBzimmT_uTfMrEXjxsPh2mtRQr7y0oRy8ClYEsexl02WuwEE0LO9FNZBL0k2fmkdM47QVS_9PD97PQIE35ew3wn3TnlYmnneT-kI8ykFkj15LmYOF6b7M6_ZB4sIXQ3aCV0PXJ4umtMxmCyfxkZ7SxsmlLfaO-Da2NwTBj9MWAAMus4oSO4Qn2MzXue_qNAwh-Wwufzm8OHOpvE8x2sOhOZHbb4SmkvZN4TmRSdk6e9CEZpzydQBomjYUCR7YqaJlFYYISsERA0zvB5e98uogYiDQ-tiDpGGCKL_Q_QxHVbzMQ4P-eoiCE5_caWGwA5v45aV_jWhWUqvkbYrhnvr_XUHEFvWo5-73Jmlx0hz8Rm0na3htcELAbqqBRgAtr0ebXQf7pPRkeL5DwRPxllZxkdPGDbAQEtotjqhrGuG9RJC0zC23JnwYGi4ZjcG_IDxBWVPkDuinbms-gjkYWdb8jBZRpamvsKMVrpgG90fAyg9j6UPyTUPb9rRWia9Hi3w2xCV97tdsqdT2mHtbCv1EU26INk2fh9bZ26CNlZxC4_Tmwnuir9r27f53Qv5FHuH3AZyet7CE48UEvZ75g_Y_pRyhgN0csH08LCyfHOHtboN--GtTX_DMT1WxfMp6mZymn1ae5E0Ocg_cybPKt86mn_pTJ5HewVXW3B-jkchB0S-eiVA59OR3DgUrqS2_CL14pe7-flLjVAaVjnY7t6BbZGHHH2qOr461M611vuT5oTmB-Hqroi59pl5-_lDZHXljswgoTkrRMQYoXnbSUlonq5TQvNKSLS-vFj23YKrmQNXIyitIl_iRCU4Uw4K4Swwg9Apr0JUAktvSdEN-MNtIclX4NsUZtAGSLqICuGA15366pVLzUos4ShcHcbfP33-Hwhlnem472O8KK6VY0IJdQgQZg5dg8qFJiQbaxkEOg3Mz_HNk4NjLXgNNfPLa4sDxKLzsN_RaK9_wFRMSAsFctZZHAqvNz7CZ4fKi_SL90x2CEI5PeILGwidOylsPHcaj0OY-4Yr-LNnRrBScOjRWN-o6SoQV506GfwIRwRshAMGZJHs8keySMY-8fRcIjNh4o39BVba4MntZ0kvZoYe0hjk7hf0bfs9c86IonM4dEBKCyWFwlOb9Hpz93pTdt3y_VPt1d_YX_1bGqhz0q74derznh8e1q9UyOTHdXroPiajwgF-m5aMoXZfSkaoX-mN9l9SzP9MJR-T_1Qxv1Ty5cQDp_vdan5TKGblJivX2ZrNcJMuVul6tVisF7N6k_ISM7qkc75eccbW62XJlpSvCz5HXCGbiQ1NaJbMaZImWZot4uUDZvNVwbLioUoq5GSeYMOEjP0ejbU5zIS1HW4WlC7SmWQFShu-WCm9fI2yIYdR_xVrNn5iVHQHS-aJ_zCzL1ROOImbD1fzfC48V7XWm10Cs3DJmOfEP-uM3LxR8k5HKizeGv2bT3U0D9otoXmQ_0cAAAD__4nHM-A">