summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorKinsey Moore <kinsey.moore@oarcorp.com>2022-10-25 12:41:27 -0500
committerJoel Sherrill <joel@rtems.org>2022-11-09 08:14:11 -0600
commit080dc5d873773f65a6cc89c80f4338fc929796a8 (patch)
tree9aea4402ab252588430b5ba4f6a2ca58fb6c16c6
parentbsps/aarch64: Ensure FPU trap state is consistent (diff)
downloadrtems-080dc5d873773f65a6cc89c80f4338fc929796a8.tar.bz2
cpukit/aarch64: Emulate FPSR for FENV traps
The AArch64 TRM specifies that when FPCR is set to trap floating point exceptions, the FPSR exception bits are not set. This ensures that FPSR is updated as FENV expects even if floating point exception traps are enabled.
-rw-r--r--cpukit/score/cpu/aarch64/aarch64-exception-default.c20
1 files changed, 20 insertions, 0 deletions
diff --git a/cpukit/score/cpu/aarch64/aarch64-exception-default.c b/cpukit/score/cpu/aarch64/aarch64-exception-default.c
index 3494c88ea6..f1591cbd5d 100644
--- a/cpukit/score/cpu/aarch64/aarch64-exception-default.c
+++ b/cpukit/score/cpu/aarch64/aarch64-exception-default.c
@@ -48,6 +48,26 @@
void _AArch64_Exception_default( CPU_Exception_frame *frame )
{
+ uint64_t EC = AARCH64_ESR_EL1_EC_GET( frame->register_syndrome );
+
+ /* Emulate FPSR flags for FENV if a FPU exception occurred */
+ if ( EC == 0x2c ) {
+ /*
+ * This must be done because FENV depends on FPSR values, but trapped FPU
+ * exceptions don't set FPSR bits. In the case where a signal is mapped, the
+ * signal code executes after the exception frame is restored and FENV
+ * functions executed in that context will need this information to be
+ * accurate.
+ */
+ uint64_t ISS = AARCH64_ESR_EL1_EC_GET( frame->register_syndrome );
+
+ /* If the exception bits are valid, use them */
+ if ( ( ISS & ( 1 << 23 ) ) != 0 ) {
+ /* The bits of the lower byte match the FPSR exception bits */
+ frame->register_fpsr |= ( ISS & 0xff );
+ }
+ }
+
rtems_fatal( RTEMS_FATAL_SOURCE_EXCEPTION, (rtems_fatal_code) frame );
}