Exception Handling when arguments are passed on the stack
When arguments are passed on the stack to a call whose exception-clause/catch-block is executed (due to an exception being thrown) the stack pointer is incorrectly restored. This can be demonstrated with the simple program:
.funcsig stack_sig = (int<64> int<64> int<64> int<64> int<64> int<64> int<64>)->()
.funcdef stack_args <stack_sig>
{
entry(<int<64>> v0 <int<64>> v1 <int<64>> v2 <int<64>> v3 <int<64>> v4 <int<64>> v5 <int<64>> v6):
THROW <ref<void>> NULL
}
.funcdef test_except_stack_args <main_sig>
{
entry(<int<32>>argc <uptr<uptr<char>>>argv):
CALL <stack_sig> stack_args(<int<32>>0 <int<32>>1 <int<32>>2 <int<32>>3 <int<32>>4 <int<32>>5 <int<32>>6)
EXC (exit(<int<32>> 0) exit(<int<32>> 1))
exit(<int<32>> status):
RET status
}
(testable with pytest tests/test_muc/test_simple.py::test_except_stack_args
).
This segfaults on x86-64 (which only has 6 argument registers, so the call to stack_args passes some arguments to the stack), but it works as expected on aarch64 (which has 8 argument registers, so nothing is passed on the stack).