1
Fork 0
mirror of https://git.savannah.gnu.org/git/guile.git synced 2025-06-15 08:10:17 +02:00

Correct regression with float arguments in arm hardp

* lib/jit_arm.c: Correct jit_pushargi_f in the arm hardfp abi.
	Most of the logic uses even numbered register numbers, so that
	a float and a double can be used in the same register, but
	the abi requires packing the float arguments, so jit_pushargi_f
	needs to allocate a temporary register to modify only the
	proper register argument (or be very smart to push two
	immediate arguments if applicable).
This commit is contained in:
pcpa 2013-02-11 17:39:06 -02:00
parent 8f020fe044
commit 12c35b7e83
2 changed files with 25 additions and 9 deletions

View file

@ -1,3 +1,13 @@
2013-02-11 Paulo Andrade <pcpa@gnu.org>
* lib/jit_arm.c: Correct jit_pushargi_f in the arm hardfp abi.
Most of the logic uses even numbered register numbers, so that
a float and a double can be used in the same register, but
the abi requires packing the float arguments, so jit_pushargi_f
needs to allocate a temporary register to modify only the
proper register argument (or be very smart to push two
immediate arguments if applicable).
2013-02-11 Paulo Andrade <pcpa@gnu.org> 2013-02-11 Paulo Andrade <pcpa@gnu.org>
* include/lightning.h, lib/lightning.c: Implement the new * include/lightning.h, lib/lightning.c: Implement the new

View file

@ -386,21 +386,20 @@ _jit_arg_f(jit_state_t *_jit)
assert(_jit->function); assert(_jit->function);
if (jit_cpu.abi && !(_jit->function->self.call & jit_call_varargs)) { if (jit_cpu.abi && !(_jit->function->self.call & jit_call_varargs)) {
if (_jit->function->self.argf < 16) if (_jit->function->self.argf < 16) {
offset = _jit->function->self.argf++; offset = _jit->function->self.argf++;
else { goto done;
offset = _jit->function->self.size;
_jit->function->self.size += sizeof(jit_word_t);
} }
} }
else { else {
if (_jit->function->self.argi < 4) if (_jit->function->self.argi < 4) {
offset = _jit->function->self.argi++; offset = _jit->function->self.argi++;
else { goto done;
}
}
offset = _jit->function->self.size; offset = _jit->function->self.size;
_jit->function->self.size += sizeof(jit_float32_t); _jit->function->self.size += sizeof(jit_float32_t);
} done:
}
return (jit_new_node_w(jit_code_arg_f, offset)); return (jit_new_node_w(jit_code_arg_f, offset));
} }
@ -604,7 +603,14 @@ _jit_pushargi_f(jit_state_t *_jit, jit_float32_t u)
assert(_jit->function); assert(_jit->function);
if (jit_cpu.abi && !(_jit->function->call.call & jit_call_varargs)) { if (jit_cpu.abi && !(_jit->function->call.call & jit_call_varargs)) {
if (_jit->function->call.argf < 16) { if (_jit->function->call.argf < 16) {
jit_movi_f(JIT_FA0 - _jit->function->call.argf, u); /* cannot jit_movi_f in the argument register because
* float arguments are packed, and that would cause
* either an assertion in debug mode, or overwritting
* two registers */
regno = jit_get_reg(jit_class_fpr);
jit_movi_f(regno, u);
jit_movr_f(JIT_FA0 - _jit->function->call.argf, regno);
jit_unget_reg(regno);
++_jit->function->call.argf; ++_jit->function->call.argf;
return; return;
} }