xref: /freebsd-src/contrib/llvm-project/compiler-rt/lib/builtins/riscv/fp_mode.c (revision bdd1243df58e60e85101c09001d9812a789b6bc4)
1*bdd1243dSDimitry Andric //=== lib/builtins/riscv/fp_mode.c - Floaing-point mode utilities -*- C -*-===//
2*bdd1243dSDimitry Andric //
3*bdd1243dSDimitry Andric // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4*bdd1243dSDimitry Andric // See https://llvm.org/LICENSE.txt for license information.
5*bdd1243dSDimitry Andric // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6*bdd1243dSDimitry Andric //
7*bdd1243dSDimitry Andric //===----------------------------------------------------------------------===//
8*bdd1243dSDimitry Andric #include "../fp_mode.h"
9*bdd1243dSDimitry Andric 
10*bdd1243dSDimitry Andric #define RISCV_TONEAREST  0x0
11*bdd1243dSDimitry Andric #define RISCV_TOWARDZERO 0x1
12*bdd1243dSDimitry Andric #define RISCV_DOWNWARD   0x2
13*bdd1243dSDimitry Andric #define RISCV_UPWARD     0x3
14*bdd1243dSDimitry Andric 
15*bdd1243dSDimitry Andric #define RISCV_INEXACT    0x1
16*bdd1243dSDimitry Andric 
17*bdd1243dSDimitry Andric CRT_FE_ROUND_MODE __fe_getround(void) {
18*bdd1243dSDimitry Andric #if defined(__riscv_f)
19*bdd1243dSDimitry Andric   int frm;
20*bdd1243dSDimitry Andric   __asm__ __volatile__("frrm %0" : "=r" (frm));
21*bdd1243dSDimitry Andric   switch (frm) {
22*bdd1243dSDimitry Andric     case RISCV_TOWARDZERO:
23*bdd1243dSDimitry Andric       return CRT_FE_TOWARDZERO;
24*bdd1243dSDimitry Andric     case RISCV_DOWNWARD:
25*bdd1243dSDimitry Andric       return CRT_FE_DOWNWARD;
26*bdd1243dSDimitry Andric     case RISCV_UPWARD:
27*bdd1243dSDimitry Andric       return CRT_FE_UPWARD;
28*bdd1243dSDimitry Andric     case RISCV_TONEAREST:
29*bdd1243dSDimitry Andric     default:
30*bdd1243dSDimitry Andric       return CRT_FE_TONEAREST;
31*bdd1243dSDimitry Andric   }
32*bdd1243dSDimitry Andric #else
33*bdd1243dSDimitry Andric   return CRT_FE_TONEAREST;
34*bdd1243dSDimitry Andric #endif
35*bdd1243dSDimitry Andric }
36*bdd1243dSDimitry Andric 
37*bdd1243dSDimitry Andric int __fe_raise_inexact(void) {
38*bdd1243dSDimitry Andric #if defined(__riscv_f)
39*bdd1243dSDimitry Andric   __asm__ __volatile__("csrsi fflags, %0" :: "i" (RISCV_INEXACT));
40*bdd1243dSDimitry Andric #endif
41*bdd1243dSDimitry Andric   return 0;
42*bdd1243dSDimitry Andric }
43