On Wed, Jul 02, 2014 at 06:50:27AM +0100, Al Viro wrote: > AFAICS, it leaves two possibilities - EV45 (AS200) vs. EV6 (DS10) and EV67 > (qemu) _or_ some change in the kernel. I'll build 3.x kernel for DS10 and > post the results; shouldn't take long...
Actually, it's simpler - note that on *all* systems we end up with FPCR.INE set. So this swcr_update_status(unsigned long swcr, unsigned long fpcr) { /* EV6 implements most of the bits in hardware. Collect the acrued exception bits from the real fpcr. */ if (implver() == IMPLVER_EV6) { swcr &= ~IEEE_STATUS_MASK; swcr |= (fpcr >> 35) & IEEE_STATUS_MASK; } return swcr; } ends up with FE_INEXACT set on everything that has implver() return 2. Which is what EV6 and EV67 do and which is what qemu does by default. So no, it's not a kernel version difference; it's all kernel versions ignoring FPCR.INE when it calculates ieee_state on EV45 and using it on EV6 and friends. If we don't want FE_INEXACT seen by fetestexcept() after rounding 4.5, we'd better not use FPCR.INE - *all* variants of actual hardware (at least from 21064A to 21264) set that sucker, and 4.7 in Architecture Reference Manual very clearly requires such behaviour for any subset that isn't completely without floating point support.