1#include <float.h>
2#include <math.h>
3#include <stdint.h>
4
5#if FLT_EVAL_METHOD == 0 || FLT_EVAL_METHOD == 1
6#define EPS DBL_EPSILON
7#elif FLT_EVAL_METHOD == 2
8#define EPS LDBL_EPSILON
9#endif
10static const double_t toint = 1 / EPS;
11
12double rint(double x) {
13    union {
14        double f;
15        uint64_t i;
16    } u = {x};
17    int e = u.i >> 52 & 0x7ff;
18    int s = u.i >> 63;
19    double_t y;
20
21    if (e >= 0x3ff + 52)
22        return x;
23    if (s)
24        y = x - toint + toint;
25    else
26        y = x + toint - toint;
27    if (y == 0)
28        return s ? -0.0 : 0;
29    return y;
30}
31