<table border="1" cellspacing="0" cellpadding="8">
<tr>
<th>Issue</th>
<td>
<a href=https://github.com/llvm/llvm-project/issues/151581>151581</a>
</td>
</tr>
<tr>
<th>Summary</th>
<td>
`[[musttail]]` Silently ignored in some cases in conjuction with the `flatten` attribute
</td>
</tr>
<tr>
<th>Labels</th>
<td>
new issue
</td>
</tr>
<tr>
<th>Assignees</th>
<td>
</td>
</tr>
<tr>
<th>Reporter</th>
<td>
Hendiadyoin1
</td>
</tr>
</table>
<pre>
In <https://github.com/LadybirdBrowser/ladybird/pull/5641>
I have found that `[[musttail]]` is silently ignored in some cases.
To describe what the linked code does
It moves a jump-threading bytecode interpreter to a similar model, trying to do tail-calls to member pointers instead,
each dispatch function is flattened to squeeze out a bit more performance, yielding:
```c++
#define DISPATCH_NEXT() \
do { \
auto& next_instruction = *reinterpret_cast<Instruction const*>(&bytecode[program_counter]); \
auto fn = dispatch_instruction_table[static_cast<size_t>(next_instruction.type())]; \
[[clang::musttail]] return (this->*fn)(bytecode, program_counter); \
} while (0)
template<typename OP>
ALWAYS_INLINE FLATTEN void Interpreter::handle_with_exception_check(u8 const* bytecode, size_t& program_counter)
{
{
auto const& instruction = *reinterpret_cast<OP const*>(&bytecode[program_counter]);
auto result = instruction.execute_impl(*this);
if (result.is_error()) [[unlikely]] {
if (handle_exception(program_counter, result.error_value()) == HandleExceptionResponse::ExitFromExecutable)
return;
DISPATCH_NEXT();
}
increment_program_counter(program_counter, instruction);
}
DISPATCH_NEXT();
}
#define HANDLE_INSTRUCTION(name) \
FLATTEN void Interpreter::handle_##name(u8 const* bytecode, size_t& program_counter) \
{ \
return handle_with_exception_check<Op::name>(bytecode, program_counter); \
}
HANDLE_INSTRUCTION(OP1);
HANDLE_INSTRUCTION(OP2);
...
```
as a rough implementation
removing the `FLATTEN` seems to make it work, so my guess is that it inlines some functions requiring some more cleanup, which somehow inhibits the tail-call, not sure what happens with the diagnostic though
I was not yet able to craft a small reproducer
</pre>
<img width="1" height="1" alt="" src="http://email.email.llvm.org/o/eJycVl9v464S_TTkZdTIwc2_hzw4_9RIVVv92qt771OEzSRmi8EL46bZT_8T2EmT3W61WmSpjQ1nzjkzMAjv1d4gzthwzobLnmiotG52h0YqIY9WmUEvt_I42xhg6aIkqj1LM8bXjK_3isom7xe2Ynx9L-QxV07OnT14dIyvdfeG8XXdaM34eji6HbB0xZJsA6V4Q9jZxkigUhCwURI5zKvGEwml2XAZnlECyoNXGg3pI6i9sQ4lKAPeVgiF8Oj7LMlYkr1YkOgLp3KEQ8CkEkEr84oSCisRpEUfghNU9g09CPjWVPUNlQ6FVGYP-ZEwzlSG0NUOCR2QBQFeVUoLB5WVqBlfALljWEEWpIXA96YQWvvwosIqRwe1jSgelPGEQjK-YEmGoihBKl8LKkrYNaYgZU3QuNOCCA3KgOG_N4g_EGxDICBXgbJDqNHtrKuEKTCQOCrUgXhISZIFC-NTMD4PT5IxnkrcKYOw3Dw_ZS-Lu-3D6n8vjE8YnwIbBkYQh7TAxvPTK9GQZXwEBt9pG_i7puXJ0iUwnjk8O7QthCeWLjYXswprPDGehWSHUKOTsWw4r53dO1FtC9sEiJBjPmXp_IpNGIED7NqQJ8MuuWxJ5DogehKkihMPr37gltrIP9Pv07HGVnx4hsvP4rZlWGjR-ppm1xUJDqlxBhifUKn8TYyU7UzEnJyF8gX8rLSV-dtxyYONl3AolcYQJgkrY4UTVrUWhCxdBCVGVAiPT-2Wyu7_m_3_ebt5uN88rGB9n728rB7gzSoJm49qbhWVwkiN24OicovvBdbRz6LE4pXxSTM5JxAu9XTO8tFnypKMjecd_4__znnsAEfwZ8X0-PRXNfRzVIe-0RTjXFYBvmPREG5VVeuInYVM_gKhdsH9FqOv_Bads-5cPV2dNEarV9THrjiupX-gdI6fzWZ88ouJi45vPwbavgnd4EW4dBl03EWg1QnnH_S1NR7bvK7eFa2drVZRYNweMTVdzV7LC-OTU-F6Ehsvwy9lCocVGtr-wvozHRdmXyF2aL-N2n6_Orfusofl_Wq7eXh--ec_i5fN40PY16LC6wPsj-qd8ZTxtF38V1V-CnhxUnajOxS-2ljp4rFu6UQGsaz__Lg4R-4c-tSXx6fB2cvfTODnCf1-_7JpsCQToSU62-xLCFsjJlzEJMaQDiv7FpteiaFfd56HFu0Rq7b3iVcERXCw7jW6aaE6wr5B70OPi61eESijlUHf9vBTE_Tg8HujXAgRP8SWV2gUpqkD2KFURRk_lfYAypQqV-QjnXMHDvOMJfCN624BpahrNB5CUuJcqcTeWE-qACqD2lbeBg7Cx7VHJAibJwgqnNiFFuwroTU4rJ2VTYGOJVlPzlI5Taeih7PBeJhOJ9PxlPfK2W60m0xlIiajWz7NJ7spFxMxkIkc5CMucdhTM57wYTJOB4MpTwe8P07G09E0EYNJmo4H45TdJlgJpftav1V96_Y95X2Ds8FwMJwMelrkqH28tHFu8ADxK-M83OHcLCy6yZu9Z7eJVp78Bwwp0jj74rL1_OVNK_wqrPnWHeBnS9ko6a4vAUMQOZU3hL3G6dkXl8ZAq_tzUzv7DQtifB3FeMbXndq3Gf83AAD__-vqXOU">