1 #ifndef SPARC_FENV_PRIVATE_H
2 #define SPARC_FENV_PRIVATE_H 1
6 /* For internal use only: access the fp state register. */
8 # define __fenv_stfsr(X) __asm__ __volatile__ ("stx %%fsr,%0" : "=m" (X))
9 # define __fenv_ldfsr(X) __asm__ __volatile__ ("ldx %0,%%fsr" : : "m" (X))
11 # define __fenv_stfsr(X) __asm__ __volatile__ ("st %%fsr,%0" : "=m" (X))
12 # define __fenv_ldfsr(X) __asm__ __volatile__ ("ld %0,%%fsr" : : "m" (X))
15 static __always_inline
void
16 libc_feholdexcept (fenv_t
*e
)
21 etmp
= etmp
& ~((0x1f << 23) | FE_ALL_EXCEPT
);
25 static __always_inline
void
26 libc_fesetround (int r
)
30 etmp
= (etmp
& ~__FE_ROUND_MASK
) | (r
);
34 static __always_inline
void
35 libc_feholdexcept_setround (fenv_t
*e
, int r
)
40 etmp
= etmp
& ~((0x1f << 23) | FE_ALL_EXCEPT
);
41 etmp
= (etmp
& ~__FE_ROUND_MASK
) | (r
);
45 static __always_inline
int
46 libc_fetestexcept (int e
)
50 return etmp
& (e
) & FE_ALL_EXCEPT
;
53 static __always_inline
void
54 libc_fesetenv (fenv_t
*e
)
59 static __always_inline
int
60 libc_feupdateenv_test (fenv_t
*e
, int ex
)
65 etmp
&= FE_ALL_EXCEPT
;
69 __feraiseexcept (etmp
);
74 static __always_inline
void
75 libc_feupdateenv (fenv_t
*e
)
77 libc_feupdateenv_test (e
, 0);
80 static __always_inline
void
81 libc_feholdsetround (fenv_t
*e
, int r
)
86 etmp
= (etmp
& ~__FE_ROUND_MASK
) | (r
);
90 static __always_inline
void
91 libc_feresetround (fenv_t
*e
)
95 etmp
= (etmp
& ~__FE_ROUND_MASK
) | (*e
& __FE_ROUND_MASK
);
99 #define libc_feholdexceptf libc_feholdexcept
100 #define libc_fesetroundf libc_fesetround
101 #define libc_feholdexcept_setroundf libc_feholdexcept_setround
102 #define libc_fetestexceptf libc_fetestexcept
103 #define libc_fesetenvf libc_fesetenv
104 #define libc_feupdateenv_testf libc_feupdateenv_test
105 #define libc_feupdateenvf libc_feupdateenv
106 #define libc_feholdsetroundf libc_feholdsetround
107 #define libc_feresetroundf libc_feresetround
108 #define libc_feholdexcept libc_feholdexcept
109 #define libc_fesetround libc_fesetround
110 #define libc_feholdexcept_setround libc_feholdexcept_setround
111 #define libc_fetestexcept libc_fetestexcept
112 #define libc_fesetenv libc_fesetenv
113 #define libc_feupdateenv_test libc_feupdateenv_test
114 #define libc_feupdateenv libc_feupdateenv
115 #define libc_feholdsetround libc_feholdsetround
116 #define libc_feresetround libc_feresetround
117 #define libc_feholdexceptl libc_feholdexcept
118 #define libc_fesetroundl libc_fesetround
119 #define libc_feholdexcept_setroundl libc_feholdexcept_setround
120 #define libc_fetestexceptl libc_fetestexcept
121 #define libc_fesetenvl libc_fesetenv
122 #define libc_feupdateenv_testl libc_feupdateenv_test
123 #define libc_feupdateenvl libc_feupdateenv
124 #define libc_feholdsetroundl libc_feholdsetround
125 #define libc_feresetroundl libc_feresetround
127 /* We have support for rounding mode context. */
128 #define HAVE_RM_CTX 1
130 static __always_inline
void
131 libc_feholdexcept_setround_sparc_ctx (struct rm_ctx
*ctx
, int round
)
135 __fenv_stfsr(ctx
->env
);
136 new = ctx
->env
& ~((0x1f << 23) | FE_ALL_EXCEPT
);
137 new = (new & ~__FE_ROUND_MASK
) | round
;
138 if (__glibc_unlikely (new != ctx
->env
))
141 ctx
->updated_status
= true;
144 ctx
->updated_status
= false;
147 static __always_inline
void
148 libc_fesetenv_sparc_ctx (struct rm_ctx
*ctx
)
150 libc_fesetenv(&ctx
->env
);
153 static __always_inline
void
154 libc_feupdateenv_sparc_ctx (struct rm_ctx
*ctx
)
156 if (__glibc_unlikely (ctx
->updated_status
))
157 libc_feupdateenv_test (&ctx
->env
, 0);
160 static __always_inline
void
161 libc_feholdsetround_sparc_ctx (struct rm_ctx
*ctx
, int round
)
165 __fenv_stfsr(ctx
->env
);
166 new = (ctx
->env
& ~__FE_ROUND_MASK
) | round
;
167 if (__glibc_unlikely (new != ctx
->env
))
170 ctx
->updated_status
= true;
173 ctx
->updated_status
= false;
175 #define libc_feholdexcept_setround_ctx libc_feholdexcept_setround_sparc_ctx
176 #define libc_feholdexcept_setroundf_ctx libc_feholdexcept_setround_sparc_ctx
177 #define libc_feholdexcept_setroundl_ctx libc_feholdexcept_setround_sparc_ctx
178 #define libc_fesetenv_ctx libc_fesetenv_sparc_ctx
179 #define libc_fesetenvf_ctx libc_fesetenv_sparc_ctx
180 #define libc_fesetenvl_ctx libc_fesetenv_sparc_ctx
181 #define libc_feupdateenv_ctx libc_feupdateenv_sparc_ctx
182 #define libc_feupdateenvf_ctx libc_feupdateenv_sparc_ctx
183 #define libc_feupdateenvl_ctx libc_feupdateenv_sparc_ctx
184 #define libc_feresetround_ctx libc_feupdateenv_sparc_ctx
185 #define libc_feresetroundf_ctx libc_feupdateenv_sparc_ctx
186 #define libc_feresetroundl_ctx libc_feupdateenv_sparc_ctx
187 #define libc_feholdsetround_ctx libc_feholdsetround_sparc_ctx
188 #define libc_feholdsetroundf_ctx libc_feholdsetround_sparc_ctx
189 #define libc_feholdsetroundl_ctx libc_feholdsetround_sparc_ctx
191 #include_next <fenv_private.h>
193 #endif /* SPARC_FENV_PRIVATE_H */