From a05958934a426a8da179e0177feaee9c59935213 Mon Sep 17 00:00:00 2001 From: lkcl Date: Fri, 21 Apr 2023 23:10:42 +0100 Subject: [PATCH] --- openpower/sv/rfc/ls013.mdwn | 35 ++++++++++++++++++++++++++++++++++- 1 file changed, 34 insertions(+), 1 deletion(-) diff --git a/openpower/sv/rfc/ls013.mdwn b/openpower/sv/rfc/ls013.mdwn index e6e77bd71..0e2a2f606 100644 --- a/openpower/sv/rfc/ls013.mdwn +++ b/openpower/sv/rfc/ls013.mdwn @@ -327,8 +327,41 @@ Add `MM` to the `Formats:` list for all of `FRT`, `FRA`, `FRB`, `XO (25:30)`, ## fmax instruction count 32 instructions are required in SFFS to emulate fmax. - +``` +#include +#include + +inline uint64_t asuint64(double f) { + union { + double f; + uint64_t i; + } u = {f}; + return u.i; +} + +inline int issignaling(double v) { + // copied from glibc: + // https://github.com/bminor/glibc/blob/e2756903329365134089d23548e9083d23bc3dd9/sysdeps/ieee754/dbl-64/math_config.h#L101 + uint64_t ix = asuint64(v); + return 2 * (ix ^ 0x0008000000000000) > 2 * 0x7ff8000000000000ULL; +} + +double fmax(double x, double y) { + // copied from glibc: + // https://github.com/bminor/glibc/blob/e2756903329365134089d23548e9083d23bc3dd9/math/s_fmax_template.c + if(__builtin_isgreaterequal(x, y)) + return x; + else if(__builtin_isless(x, y)) + return y; + else if(issignaling(x) || issignaling(y)) + return x + y; + else + return __builtin_isnan(y) ? x : y; +} +``` + +Assembly listing: ``` fmax(double, double): -- 2.30.2