libgcc/ChangeLog:

        * Makefile.in: Support __divbc3 and __mulbc3.
        * libgcc2.c (if): Support BC mode for __bf16.
        (defined): Ditto.
        (MTYPE): Ditto.
        (CTYPE): Ditto.
        (AMTYPE): Ditto.
        (MODE): Ditto.
        (CEXT): Ditto.
        (NOTRUNC): Ditto.
        * libgcc2.h (LIBGCC2_HAS_BF_MODE): Ditto.
        (__attribute__): Ditto.
        (__divbc3): Add __divbc3 for __bf16.
        (__mulbc3): Add __mulbc3 for __bf16.

gcc/testsuite/ChangeLog:

        * gcc.target/riscv/bf16-mulbc3-divbc3.c: New test.

Signed-off-by: Xiao Zeng <zengx...@eswincomputing.com>
---
 .../gcc.target/riscv/bf16-mulbc3-divbc3.c     | 31 +++++++++++++++++++
 libgcc/Makefile.in                            |  6 ++--
 libgcc/libgcc2.c                              | 20 ++++++++----
 libgcc/libgcc2.h                              | 14 +++++++++
 4 files changed, 62 insertions(+), 9 deletions(-)
 create mode 100644 gcc/testsuite/gcc.target/riscv/bf16-mulbc3-divbc3.c

diff --git a/gcc/testsuite/gcc.target/riscv/bf16-mulbc3-divbc3.c 
b/gcc/testsuite/gcc.target/riscv/bf16-mulbc3-divbc3.c
new file mode 100644
index 00000000000..5b30de15ccf
--- /dev/null
+++ b/gcc/testsuite/gcc.target/riscv/bf16-mulbc3-divbc3.c
@@ -0,0 +1,31 @@
+/* { dg-do run } */
+/* { dg-options "" } */
+/* { dg-skip-if "" { *-*-* } { "-O0" } } */
+#include <complex.h>
+
+typedef _Complex float __cbf16 __attribute__((__mode__(__BC__)));
+
+__cbf16
+divbc3 (__cbf16 rs1, __cbf16 rs2)
+{
+  return rs1 / rs2;
+}
+
+__cbf16
+mulbc3 (__cbf16 rs1, __cbf16 rs2)
+{
+  return rs1 * rs2;
+}
+
+int main()
+{
+  __cbf16 rs1 = 2.0 + 4.0 * I;
+  __cbf16 rs2 = 1.0 + 2.0 * I;
+  __cbf16 mul = -6.0 + 8.0 * I;
+  __cbf16 div = 2.0 + 0.0 * I;
+  if (mulbc3 (rs1, rs2) != mul)
+    __builtin_abort();
+  if (divbc3 (rs1, rs2) != div)
+    __builtin_abort();
+  return 0;
+}
diff --git a/libgcc/Makefile.in b/libgcc/Makefile.in
index 0e46e9ef768..b71fd5e2250 100644
--- a/libgcc/Makefile.in
+++ b/libgcc/Makefile.in
@@ -450,9 +450,9 @@ lib2funcs = _muldi3 _negdi2 _lshrdi3 _ashldi3 _ashrdi3 
_cmpdi2 _ucmpdi2        \
            _negvsi2 _negvdi2 _ctors _ffssi2 _ffsdi2 _clz _clzsi2 _clzdi2  \
            _ctzsi2 _ctzdi2 _popcount_tab _popcountsi2 _popcountdi2        \
            _paritysi2 _paritydi2 _powisf2 _powidf2 _powixf2 _powitf2      \
-           _mulhc3 _mulsc3 _muldc3 _mulxc3 _multc3 _divhc3 _divsc3        \
-           _divdc3 _divxc3 _divtc3 _bswapsi2 _bswapdi2 _clrsbsi2          \
-           _clrsbdi2 _mulbitint3
+           _mulhc3 _mulbc3 _mulsc3 _muldc3 _mulxc3 _multc3 _divhc3        \
+           _divbc3 _divsc3 _divdc3 _divxc3 _divtc3 _bswapsi2 _bswapdi2    \
+           _clrsbsi2 _clrsbdi2 _mulbitint3
 
 # The floating-point conversion routines that involve a single-word integer.
 # XX stands for the integer mode.
diff --git a/libgcc/libgcc2.c b/libgcc/libgcc2.c
index 3fcb85c5b92..1d2aafcfd63 100644
--- a/libgcc/libgcc2.c
+++ b/libgcc/libgcc2.c
@@ -2591,6 +2591,7 @@ NAME (TYPE x, int m)
 #endif
 
 #if((defined(L_mulhc3) || defined(L_divhc3)) && LIBGCC2_HAS_HF_MODE) \
+    || ((defined(L_mulbc3) || defined(L_divbc3)) && LIBGCC2_HAS_BF_MODE) \
     || ((defined(L_mulsc3) || defined(L_divsc3)) && LIBGCC2_HAS_SF_MODE) \
     || ((defined(L_muldc3) || defined(L_divdc3)) && LIBGCC2_HAS_DF_MODE) \
     || ((defined(L_mulxc3) || defined(L_divxc3)) && LIBGCC2_HAS_XF_MODE) \
@@ -2607,6 +2608,13 @@ NAME (TYPE x, int m)
 # define MODE  hc
 # define CEXT  __LIBGCC_HF_FUNC_EXT__
 # define NOTRUNC (!__LIBGCC_HF_EXCESS_PRECISION__)
+#elif defined(L_mulbc3) || defined(L_divbc3)
+# define MTYPE  BFtype
+# define CTYPE  BCtype
+# define AMTYPE SFtype
+# define MODE   bc
+# define CEXT   __LIBGCC_BF_FUNC_EXT__
+# define NOTRUNC (!__LIBGCC_BF_EXCESS_PRECISION__)
 #elif defined(L_mulsc3) || defined(L_divsc3)
 # define MTYPE SFtype
 # define CTYPE SCtype
@@ -2690,8 +2698,8 @@ extern void *compile_type_assert[sizeof(INFINITY) == 
sizeof(MTYPE) ? 1 : -1];
 # define TRUNC(x)      __asm__ ("" : "=m"(x) : "m"(x))
 #endif
 
-#if defined(L_mulhc3) || defined(L_mulsc3) || defined(L_muldc3) \
-    || defined(L_mulxc3) || defined(L_multc3)
+#if defined(L_mulhc3) || defined(L_mulbc3) || defined(L_mulsc3)  \
+    || defined(L_muldc3) || defined(L_mulxc3) || defined(L_multc3)
 
 CTYPE
 CONCAT3(__mul,MODE,3) (MTYPE a, MTYPE b, MTYPE c, MTYPE d)
@@ -2760,16 +2768,16 @@ CONCAT3(__mul,MODE,3) (MTYPE a, MTYPE b, MTYPE c, MTYPE 
d)
 }
 #endif /* complex multiply */
 
-#if defined(L_divhc3) || defined(L_divsc3) || defined(L_divdc3) \
-    || defined(L_divxc3) || defined(L_divtc3)
+#if defined(L_divhc3) || defined(L_divbc3) || defined(L_divsc3) \
+    || defined(L_divdc3) || defined(L_divxc3) || defined(L_divtc3)
 
 CTYPE
 CONCAT3(__div,MODE,3) (MTYPE a, MTYPE b, MTYPE c, MTYPE d)
 {
-#if defined(L_divhc3)                                          \
+#if (defined(L_divhc3) || defined(L_divbc3) )                  \
   || (defined(L_divsc3) && defined(__LIBGCC_HAVE_HWDBL__) )
 
-  /* Half precision is handled with float precision.
+  /* _Float16 and __bf16 are handled with float precision.
      float is handled with double precision when double precision
      hardware is available.
      Due to the additional precision, the simple complex divide
diff --git a/libgcc/libgcc2.h b/libgcc/libgcc2.h
index b358b3a2b50..ee99badde86 100644
--- a/libgcc/libgcc2.h
+++ b/libgcc/libgcc2.h
@@ -43,6 +43,12 @@ extern void __eprintf (const char *, const char *, unsigned 
int, const char *)
 #define LIBGCC2_HAS_HF_MODE 0
 #endif
 
+#ifdef __LIBGCC_HAS_BF_MODE__
+#define LIBGCC2_HAS_BF_MODE 1
+#else
+#define LIBGCC2_HAS_BF_MODE 0
+#endif
+
 #ifdef __LIBGCC_HAS_SF_MODE__
 #define LIBGCC2_HAS_SF_MODE 1
 #else
@@ -146,6 +152,10 @@ typedef unsigned int UTItype       __attribute__ ((mode 
(TI)));
 typedef                float HFtype    __attribute__ ((mode (HF)));
 typedef _Complex float HCtype  __attribute__ ((mode (HC)));
 #endif
+#if LIBGCC2_HAS_BF_MODE
+typedef                float BFtype    __attribute__ ((mode (BF)));
+typedef _Complex float BCtype  __attribute__ ((mode (BC)));
+#endif
 #if LIBGCC2_HAS_SF_MODE
 typedef        float SFtype    __attribute__ ((mode (SF)));
 typedef _Complex float SCtype  __attribute__ ((mode (SC)));
@@ -465,6 +475,10 @@ extern SItype __negvsi2 (SItype);
 extern HCtype __divhc3 (HFtype, HFtype, HFtype, HFtype);
 extern HCtype __mulhc3 (HFtype, HFtype, HFtype, HFtype);
 #endif
+#if LIBGCC2_HAS_BF_MODE
+extern BCtype __divbc3 (BFtype, BFtype, BFtype, BFtype);
+extern BCtype __mulbc3 (BFtype, BFtype, BFtype, BFtype);
+#endif
 #if LIBGCC2_HAS_SF_MODE
 extern DWtype __fixsfdi (SFtype);
 extern SFtype __floatdisf (DWtype);
-- 
2.17.1

Reply via email to