[libc-commits] [libc] 48607d2 - [libc][stdfix] Implement divifx functions in LLVM libc (#206115)
via libc-commits
libc-commits at lists.llvm.org
Wed Jul 15 21:24:25 PDT 2026
Author: sohail
Date: 2026-07-16T09:54:19+05:30
New Revision: 48607d29847349a617d4416c7be820032881a5a0
URL: https://github.com/llvm/llvm-project/commit/48607d29847349a617d4416c7be820032881a5a0
DIFF: https://github.com/llvm/llvm-project/commit/48607d29847349a617d4416c7be820032881a5a0.diff
LOG: [libc][stdfix] Implement divifx functions in LLVM libc (#206115)
Fixes #129124
Added:
libc/src/stdfix/divik.cpp
libc/src/stdfix/divik.h
libc/src/stdfix/divilk.cpp
libc/src/stdfix/divilk.h
libc/src/stdfix/divilr.cpp
libc/src/stdfix/divilr.h
libc/src/stdfix/divir.cpp
libc/src/stdfix/divir.h
libc/src/stdfix/diviuk.cpp
libc/src/stdfix/diviuk.h
libc/src/stdfix/diviulk.cpp
libc/src/stdfix/diviulk.h
libc/src/stdfix/diviulr.cpp
libc/src/stdfix/diviulr.h
libc/src/stdfix/diviur.cpp
libc/src/stdfix/diviur.h
libc/test/src/stdfix/DiviFxTest.h
libc/test/src/stdfix/divik_test.cpp
libc/test/src/stdfix/divilk_test.cpp
libc/test/src/stdfix/divilr_test.cpp
libc/test/src/stdfix/divir_test.cpp
libc/test/src/stdfix/diviuk_test.cpp
libc/test/src/stdfix/diviulk_test.cpp
libc/test/src/stdfix/diviulr_test.cpp
libc/test/src/stdfix/diviur_test.cpp
Modified:
libc/config/baremetal/arm/entrypoints.txt
libc/config/baremetal/riscv/entrypoints.txt
libc/config/linux/riscv/entrypoints.txt
libc/config/linux/x86_64/entrypoints.txt
libc/docs/headers/stdfix.rst
libc/include/stdfix.yaml
libc/src/__support/fixed_point/CMakeLists.txt
libc/src/__support/fixed_point/fx_bits.h
libc/src/__support/fixed_point/fx_rep.h
libc/src/stdfix/CMakeLists.txt
libc/test/src/stdfix/CMakeLists.txt
Removed:
################################################################################
diff --git a/libc/config/baremetal/arm/entrypoints.txt b/libc/config/baremetal/arm/entrypoints.txt
index 755e70f5d3ee8..c7632b9cca225 100644
--- a/libc/config/baremetal/arm/entrypoints.txt
+++ b/libc/config/baremetal/arm/entrypoints.txt
@@ -974,6 +974,14 @@ if(LIBC_COMPILER_HAS_FIXED_POINT)
libc.src.stdfix.idivulr
libc.src.stdfix.idivuk
libc.src.stdfix.idivulk
+ libc.src.stdfix.divir
+ libc.src.stdfix.divilr
+ libc.src.stdfix.divik
+ libc.src.stdfix.divilk
+ libc.src.stdfix.diviur
+ libc.src.stdfix.diviulr
+ libc.src.stdfix.diviuk
+ libc.src.stdfix.diviulk
)
endif()
diff --git a/libc/config/baremetal/riscv/entrypoints.txt b/libc/config/baremetal/riscv/entrypoints.txt
index 8821a22d2ccd2..5918ac2bc4282 100644
--- a/libc/config/baremetal/riscv/entrypoints.txt
+++ b/libc/config/baremetal/riscv/entrypoints.txt
@@ -971,6 +971,14 @@ if(LIBC_COMPILER_HAS_FIXED_POINT)
libc.src.stdfix.idivulr
libc.src.stdfix.idivuk
libc.src.stdfix.idivulk
+ libc.src.stdfix.divir
+ libc.src.stdfix.divilr
+ libc.src.stdfix.divik
+ libc.src.stdfix.divilk
+ libc.src.stdfix.diviur
+ libc.src.stdfix.diviulr
+ libc.src.stdfix.diviuk
+ libc.src.stdfix.diviulk
)
endif()
diff --git a/libc/config/linux/riscv/entrypoints.txt b/libc/config/linux/riscv/entrypoints.txt
index eb3f9a77b889b..c9eb605423bbc 100644
--- a/libc/config/linux/riscv/entrypoints.txt
+++ b/libc/config/linux/riscv/entrypoints.txt
@@ -1188,6 +1188,14 @@ if(LIBC_COMPILER_HAS_FIXED_POINT)
libc.src.stdfix.idivuk
libc.src.stdfix.idivulk
libc.src.stdfix.rdivi
+ libc.src.stdfix.divir
+ libc.src.stdfix.divilr
+ libc.src.stdfix.divik
+ libc.src.stdfix.divilk
+ libc.src.stdfix.diviur
+ libc.src.stdfix.diviulr
+ libc.src.stdfix.diviuk
+ libc.src.stdfix.diviulk
)
endif()
diff --git a/libc/config/linux/x86_64/entrypoints.txt b/libc/config/linux/x86_64/entrypoints.txt
index d7e4408357658..d5f9c29836939 100644
--- a/libc/config/linux/x86_64/entrypoints.txt
+++ b/libc/config/linux/x86_64/entrypoints.txt
@@ -1193,6 +1193,14 @@ if(LIBC_COMPILER_HAS_FIXED_POINT)
libc.src.stdfix.idivuk
libc.src.stdfix.idivulk
libc.src.stdfix.rdivi
+ libc.src.stdfix.divir
+ libc.src.stdfix.divilr
+ libc.src.stdfix.divik
+ libc.src.stdfix.divilk
+ libc.src.stdfix.diviur
+ libc.src.stdfix.diviulr
+ libc.src.stdfix.diviuk
+ libc.src.stdfix.diviulk
)
endif()
diff --git a/libc/docs/headers/stdfix.rst b/libc/docs/headers/stdfix.rst
index c3ac4d97650f4..91dad81c595b0 100644
--- a/libc/docs/headers/stdfix.rst
+++ b/libc/docs/headers/stdfix.rst
@@ -73,7 +73,7 @@ The following functions are included in the ISO/IEC TR 18037:2008 standard.
+---------------+----------------+-------------+---------------+------------+----------------+-------------+----------------+-------------+---------------+------------+----------------+-------------+
| countls | |check| | |check| | |check| | |check| | |check| | |check| | |check| | |check| | |check| | |check| | |check| | |check| |
+---------------+----------------+-------------+---------------+------------+----------------+-------------+----------------+-------------+---------------+------------+----------------+-------------+
-| divi\* | | | | | | | | | | | | |
+| divi\* | | | |check| | |check| | |check| | |check| | | | |check| | |check| | |check| | |check| |
+---------------+----------------+-------------+---------------+------------+----------------+-------------+----------------+-------------+---------------+------------+----------------+-------------+
| idiv\* | | | |check| | |check| | |check| | |check| | | | |check| | |check| | |check| | |check| |
+---------------+----------------+-------------+---------------+------------+----------------+-------------+----------------+-------------+---------------+------------+----------------+-------------+
diff --git a/libc/include/stdfix.yaml b/libc/include/stdfix.yaml
index 8b7485555c080..f91e4ea620e3e 100644
--- a/libc/include/stdfix.yaml
+++ b/libc/include/stdfix.yaml
@@ -565,3 +565,67 @@ functions:
- type: int
- type: int
guard: LIBC_COMPILER_HAS_FIXED_POINT
+ - name: divir
+ standards:
+ - stdc_ext
+ return_type: int
+ arguments:
+ - type: int
+ - type: fract
+ guard: LIBC_COMPILER_HAS_FIXED_POINT
+ - name: divilr
+ standards:
+ - stdc_ext
+ return_type: long int
+ arguments:
+ - type: long int
+ - type: long fract
+ guard: LIBC_COMPILER_HAS_FIXED_POINT
+ - name: divik
+ standards:
+ - stdc_ext
+ return_type: int
+ arguments:
+ - type: int
+ - type: accum
+ guard: LIBC_COMPILER_HAS_FIXED_POINT
+ - name: divilk
+ standards:
+ - stdc_ext
+ return_type: long int
+ arguments:
+ - type: long int
+ - type: long accum
+ guard: LIBC_COMPILER_HAS_FIXED_POINT
+ - name: diviur
+ standards:
+ - stdc_ext
+ return_type: unsigned int
+ arguments:
+ - type: unsigned int
+ - type: unsigned fract
+ guard: LIBC_COMPILER_HAS_FIXED_POINT
+ - name: diviulr
+ standards:
+ - stdc_ext
+ return_type: unsigned long int
+ arguments:
+ - type: unsigned long int
+ - type: unsigned long fract
+ guard: LIBC_COMPILER_HAS_FIXED_POINT
+ - name: diviuk
+ standards:
+ - stdc_ext
+ return_type: unsigned int
+ arguments:
+ - type: unsigned int
+ - type: unsigned accum
+ guard: LIBC_COMPILER_HAS_FIXED_POINT
+ - name: diviulk
+ standards:
+ - stdc_ext
+ return_type: unsigned long int
+ arguments:
+ - type: unsigned long int
+ - type: unsigned long accum
+ guard: LIBC_COMPILER_HAS_FIXED_POINT
diff --git a/libc/src/__support/fixed_point/CMakeLists.txt b/libc/src/__support/fixed_point/CMakeLists.txt
index 145eedb6ae8e7..c1b0ab30e0307 100644
--- a/libc/src/__support/fixed_point/CMakeLists.txt
+++ b/libc/src/__support/fixed_point/CMakeLists.txt
@@ -23,6 +23,7 @@ add_header_library(
libc.src.__support.CPP.bit
libc.src.__support.CPP.limits
libc.src.__support.math_extras
+ libc.src.__support.uint128
)
add_header_library(
diff --git a/libc/src/__support/fixed_point/fx_bits.h b/libc/src/__support/fixed_point/fx_bits.h
index 91814bda7dd7e..256bb3a967fbf 100644
--- a/libc/src/__support/fixed_point/fx_bits.h
+++ b/libc/src/__support/fixed_point/fx_bits.h
@@ -20,6 +20,7 @@
#include "src/__support/macros/null_check.h" // LIBC_CRASH_ON_VALUE
#include "src/__support/macros/optimization.h" // LIBC_UNLIKELY
#include "src/__support/math_extras.h"
+#include "src/__support/uint128.h"
#include "fx_rep.h"
@@ -333,6 +334,44 @@ template <typename XType> LIBC_INLINE constexpr XType divi(int n, int d) {
}
}
+// Divide an integer operand by a fixed-point operand and return the
+// mathematically exact result as an IntType rounded towards 0. Assumes
+// signedness of IntType matches the signedness of FXType.
+template <typename IntType, typename FXType>
+LIBC_INLINE constexpr cpp::enable_if_t<cpp::is_fixed_point_v<FXType>, IntType>
+divifx(IntType n, FXType d) {
+ using FXBits = FXBits<FXType>;
+ using FXRep = FXRep<FXType>;
+ using CompType = typename FXRep::CompType;
+
+ static_assert(cpp::is_signed_v<IntType> == (FXRep::SIGN_LEN > 0),
+ "IntType and FXType must have matching signedness");
+
+ // UB if denominator is 0.
+ LIBC_CRASH_ON_VALUE(d, FXRep::ZERO());
+
+ if (LIBC_UNLIKELY(n == 0)) {
+ return static_cast<IntType>(0);
+ }
+
+ CompType d_comp = static_cast<CompType>(FXBits(d).get_bits());
+
+ constexpr int F = FXRep::FRACTION_LEN;
+
+ constexpr int INTERMEDIATE_BITS =
+ sizeof(IntType) * 8 - cpp::is_signed_v<IntType> + F;
+
+ using WideType = cpp::conditional_t<
+ cpp::is_signed_v<IntType>,
+ cpp::conditional_t<INTERMEDIATE_BITS <= 64, int64_t, Int128>,
+ cpp::conditional_t<INTERMEDIATE_BITS <= 64, uint64_t, UInt128>>;
+
+ WideType scaled_n = static_cast<WideType>(n) << F;
+ WideType result = scaled_n / static_cast<WideType>(d_comp);
+
+ return static_cast<IntType>(result);
+}
+
} // namespace fixed_point
} // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/__support/fixed_point/fx_rep.h b/libc/src/__support/fixed_point/fx_rep.h
index e68be57dedf25..bdd68e54e2e77 100644
--- a/libc/src/__support/fixed_point/fx_rep.h
+++ b/libc/src/__support/fixed_point/fx_rep.h
@@ -51,6 +51,7 @@ template <> struct FXRep<short fract> {
LIBC_INLINE static constexpr Type EPS() { return SFRACT_EPSILON; }
LIBC_INLINE static constexpr Type ONE_HALF() { return 0.5HR; }
LIBC_INLINE static constexpr Type ONE_FOURTH() { return 0.25HR; }
+ LIBC_INLINE static constexpr Type ONE_EIGHTH() { return 0.125HR; }
using StorageType = typename internal::Storage<TOTAL_LEN>::Type;
using CompType = cpp::make_signed_t<StorageType>;
@@ -71,6 +72,7 @@ template <> struct FXRep<unsigned short fract> {
LIBC_INLINE static constexpr Type EPS() { return USFRACT_EPSILON; }
LIBC_INLINE static constexpr Type ONE_HALF() { return 0.5UHR; }
LIBC_INLINE static constexpr Type ONE_FOURTH() { return 0.25UHR; }
+ LIBC_INLINE static constexpr Type ONE_EIGHTH() { return 0.125UHR; }
using StorageType = typename internal::Storage<TOTAL_LEN>::Type;
using CompType = cpp::make_unsigned_t<StorageType>;
@@ -91,6 +93,7 @@ template <> struct FXRep<fract> {
LIBC_INLINE static constexpr Type EPS() { return FRACT_EPSILON; }
LIBC_INLINE static constexpr Type ONE_HALF() { return 0.5R; }
LIBC_INLINE static constexpr Type ONE_FOURTH() { return 0.25R; }
+ LIBC_INLINE static constexpr Type ONE_EIGHTH() { return 0.125R; }
using StorageType = typename internal::Storage<TOTAL_LEN>::Type;
using CompType = cpp::make_signed_t<StorageType>;
@@ -111,6 +114,7 @@ template <> struct FXRep<unsigned fract> {
LIBC_INLINE static constexpr Type EPS() { return UFRACT_EPSILON; }
LIBC_INLINE static constexpr Type ONE_HALF() { return 0.5UR; }
LIBC_INLINE static constexpr Type ONE_FOURTH() { return 0.25UR; }
+ LIBC_INLINE static constexpr Type ONE_EIGHTH() { return 0.125UR; }
using StorageType = typename internal::Storage<TOTAL_LEN>::Type;
using CompType = cpp::make_unsigned_t<StorageType>;
@@ -131,6 +135,7 @@ template <> struct FXRep<long fract> {
LIBC_INLINE static constexpr Type EPS() { return LFRACT_EPSILON; }
LIBC_INLINE static constexpr Type ONE_HALF() { return 0.5LR; }
LIBC_INLINE static constexpr Type ONE_FOURTH() { return 0.25LR; }
+ LIBC_INLINE static constexpr Type ONE_EIGHTH() { return 0.125LR; }
using StorageType = typename internal::Storage<TOTAL_LEN>::Type;
using CompType = cpp::make_signed_t<StorageType>;
@@ -151,6 +156,7 @@ template <> struct FXRep<unsigned long fract> {
LIBC_INLINE static constexpr Type EPS() { return ULFRACT_EPSILON; }
LIBC_INLINE static constexpr Type ONE_HALF() { return 0.5ULR; }
LIBC_INLINE static constexpr Type ONE_FOURTH() { return 0.25ULR; }
+ LIBC_INLINE static constexpr Type ONE_EIGHTH() { return 0.125ULR; }
using StorageType = typename internal::Storage<TOTAL_LEN>::Type;
using CompType = cpp::make_unsigned_t<StorageType>;
@@ -171,6 +177,7 @@ template <> struct FXRep<short accum> {
LIBC_INLINE static constexpr Type EPS() { return SACCUM_EPSILON; }
LIBC_INLINE static constexpr Type ONE_HALF() { return 0.5HK; }
LIBC_INLINE static constexpr Type ONE_FOURTH() { return 0.25HK; }
+ LIBC_INLINE static constexpr Type ONE_EIGHTH() { return 0.125HK; }
using StorageType = typename internal::Storage<TOTAL_LEN>::Type;
using CompType = cpp::make_signed_t<StorageType>;
@@ -191,6 +198,7 @@ template <> struct FXRep<unsigned short accum> {
LIBC_INLINE static constexpr Type EPS() { return USACCUM_EPSILON; }
LIBC_INLINE static constexpr Type ONE_HALF() { return 0.5UHK; }
LIBC_INLINE static constexpr Type ONE_FOURTH() { return 0.25UHK; }
+ LIBC_INLINE static constexpr Type ONE_EIGHTH() { return 0.125UHK; }
using StorageType = typename internal::Storage<TOTAL_LEN>::Type;
using CompType = cpp::make_unsigned_t<StorageType>;
@@ -211,6 +219,7 @@ template <> struct FXRep<accum> {
LIBC_INLINE static constexpr Type EPS() { return ACCUM_EPSILON; }
LIBC_INLINE static constexpr Type ONE_HALF() { return 0.5K; }
LIBC_INLINE static constexpr Type ONE_FOURTH() { return 0.25K; }
+ LIBC_INLINE static constexpr Type ONE_EIGHTH() { return 0.125K; }
using StorageType = typename internal::Storage<TOTAL_LEN>::Type;
using CompType = cpp::make_signed_t<StorageType>;
@@ -231,6 +240,7 @@ template <> struct FXRep<unsigned accum> {
LIBC_INLINE static constexpr Type EPS() { return UACCUM_EPSILON; }
LIBC_INLINE static constexpr Type ONE_HALF() { return 0.5UK; }
LIBC_INLINE static constexpr Type ONE_FOURTH() { return 0.25UK; }
+ LIBC_INLINE static constexpr Type ONE_EIGHTH() { return 0.125UK; }
using StorageType = typename internal::Storage<TOTAL_LEN>::Type;
using CompType = cpp::make_unsigned_t<StorageType>;
@@ -251,6 +261,7 @@ template <> struct FXRep<long accum> {
LIBC_INLINE static constexpr Type EPS() { return LACCUM_EPSILON; }
LIBC_INLINE static constexpr Type ONE_HALF() { return 0.5LK; }
LIBC_INLINE static constexpr Type ONE_FOURTH() { return 0.25LK; }
+ LIBC_INLINE static constexpr Type ONE_EIGHTH() { return 0.125LK; }
using StorageType = typename internal::Storage<TOTAL_LEN>::Type;
using CompType = cpp::make_signed_t<StorageType>;
@@ -271,6 +282,7 @@ template <> struct FXRep<unsigned long accum> {
LIBC_INLINE static constexpr Type EPS() { return ULACCUM_EPSILON; }
LIBC_INLINE static constexpr Type ONE_HALF() { return 0.5ULK; }
LIBC_INLINE static constexpr Type ONE_FOURTH() { return 0.25ULK; }
+ LIBC_INLINE static constexpr Type ONE_EIGHTH() { return 0.125ULK; }
using StorageType = typename internal::Storage<TOTAL_LEN>::Type;
using CompType = cpp::make_unsigned_t<StorageType>;
diff --git a/libc/src/stdfix/CMakeLists.txt b/libc/src/stdfix/CMakeLists.txt
index e9841cd940315..b7121407e0307 100644
--- a/libc/src/stdfix/CMakeLists.txt
+++ b/libc/src/stdfix/CMakeLists.txt
@@ -102,6 +102,20 @@ foreach(suffix IN ITEMS r)
)
endforeach()
+foreach(suffix IN ITEMS r lr k lk ur ulr uk ulk)
+ add_entrypoint_object(
+ divi${suffix}
+ HDRS
+ divi${suffix}.h
+ SRCS
+ divi${suffix}.cpp
+ COMPILE_OPTIONS
+ ${libc_opt_high_flag}
+ DEPENDS
+ libc.src.__support.fixed_point.fx_bits
+ )
+endforeach()
+
add_entrypoint_object(
uhksqrtus
HDRS
diff --git a/libc/src/stdfix/divik.cpp b/libc/src/stdfix/divik.cpp
new file mode 100644
index 0000000000000..eb6cb00d7695a
--- /dev/null
+++ b/libc/src/stdfix/divik.cpp
@@ -0,0 +1,21 @@
+//===-- Implementation of divik function ----------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "divik.h"
+#include "include/llvm-libc-macros/stdfix-macros.h"
+#include "src/__support/common.h"
+#include "src/__support/fixed_point/fx_bits.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+
+LLVM_LIBC_FUNCTION(int, divik, (int n, accum d)) {
+ return fixed_point::divifx<int, accum>(n, d);
+}
+
+} // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/stdfix/divik.h b/libc/src/stdfix/divik.h
new file mode 100644
index 0000000000000..13038b4c7e603
--- /dev/null
+++ b/libc/src/stdfix/divik.h
@@ -0,0 +1,21 @@
+//===-- Implementation header for divik -------------------------*- C++ -*-===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_LIBC_SRC_STDFIX_DIVIK_H
+#define LLVM_LIBC_SRC_STDFIX_DIVIK_H
+
+#include "include/llvm-libc-macros/stdfix-macros.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+
+int divik(int n, accum d);
+
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SRC_STDFIX_DIVIK_H
diff --git a/libc/src/stdfix/divilk.cpp b/libc/src/stdfix/divilk.cpp
new file mode 100644
index 0000000000000..cc02f56a100ae
--- /dev/null
+++ b/libc/src/stdfix/divilk.cpp
@@ -0,0 +1,21 @@
+//===-- Implementation of divilk function ---------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "divilk.h"
+#include "include/llvm-libc-macros/stdfix-macros.h"
+#include "src/__support/common.h"
+#include "src/__support/fixed_point/fx_bits.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+
+LLVM_LIBC_FUNCTION(long int, divilk, (long int n, long accum d)) {
+ return fixed_point::divifx<long int, long accum>(n, d);
+}
+
+} // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/stdfix/divilk.h b/libc/src/stdfix/divilk.h
new file mode 100644
index 0000000000000..fcb2a08fd60a9
--- /dev/null
+++ b/libc/src/stdfix/divilk.h
@@ -0,0 +1,21 @@
+//===-- Implementation header for divilk ------------------------*- C++ -*-===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_LIBC_SRC_STDFIX_DIVILK_H
+#define LLVM_LIBC_SRC_STDFIX_DIVILK_H
+
+#include "include/llvm-libc-macros/stdfix-macros.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+
+long int divilk(long int n, long accum d);
+
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SRC_STDFIX_DIVILK_H
diff --git a/libc/src/stdfix/divilr.cpp b/libc/src/stdfix/divilr.cpp
new file mode 100644
index 0000000000000..881ee63182699
--- /dev/null
+++ b/libc/src/stdfix/divilr.cpp
@@ -0,0 +1,21 @@
+//===-- Implementation of divilr function ---------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "divilr.h"
+#include "include/llvm-libc-macros/stdfix-macros.h"
+#include "src/__support/common.h"
+#include "src/__support/fixed_point/fx_bits.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+
+LLVM_LIBC_FUNCTION(long int, divilr, (long int n, long fract d)) {
+ return fixed_point::divifx<long int, long fract>(n, d);
+}
+
+} // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/stdfix/divilr.h b/libc/src/stdfix/divilr.h
new file mode 100644
index 0000000000000..348c571b7a389
--- /dev/null
+++ b/libc/src/stdfix/divilr.h
@@ -0,0 +1,21 @@
+//===-- Implementation header for divilr ------------------------*- C++ -*-===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_LIBC_SRC_STDFIX_DIVILR_H
+#define LLVM_LIBC_SRC_STDFIX_DIVILR_H
+
+#include "include/llvm-libc-macros/stdfix-macros.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+
+long int divilr(long int n, long fract d);
+
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SRC_STDFIX_DIVILR_H
diff --git a/libc/src/stdfix/divir.cpp b/libc/src/stdfix/divir.cpp
new file mode 100644
index 0000000000000..8f1c6dceb5b44
--- /dev/null
+++ b/libc/src/stdfix/divir.cpp
@@ -0,0 +1,21 @@
+//===-- Implementation of divir function ----------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "divir.h"
+#include "include/llvm-libc-macros/stdfix-macros.h"
+#include "src/__support/common.h"
+#include "src/__support/fixed_point/fx_bits.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+
+LLVM_LIBC_FUNCTION(int, divir, (int n, fract d)) {
+ return fixed_point::divifx<int, fract>(n, d);
+}
+
+} // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/stdfix/divir.h b/libc/src/stdfix/divir.h
new file mode 100644
index 0000000000000..fe2bb0e1cb278
--- /dev/null
+++ b/libc/src/stdfix/divir.h
@@ -0,0 +1,21 @@
+//===-- Implementation header for divir -------------------------*- C++ -*-===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_LIBC_SRC_STDFIX_DIVIR_H
+#define LLVM_LIBC_SRC_STDFIX_DIVIR_H
+
+#include "include/llvm-libc-macros/stdfix-macros.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+
+int divir(int n, fract d);
+
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SRC_STDFIX_DIVIR_H
diff --git a/libc/src/stdfix/diviuk.cpp b/libc/src/stdfix/diviuk.cpp
new file mode 100644
index 0000000000000..0dccbf7947b96
--- /dev/null
+++ b/libc/src/stdfix/diviuk.cpp
@@ -0,0 +1,21 @@
+//===-- Implementation of diviuk function ---------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "diviuk.h"
+#include "include/llvm-libc-macros/stdfix-macros.h"
+#include "src/__support/common.h"
+#include "src/__support/fixed_point/fx_bits.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+
+LLVM_LIBC_FUNCTION(unsigned int, diviuk, (unsigned int n, unsigned accum d)) {
+ return fixed_point::divifx<unsigned int, unsigned accum>(n, d);
+}
+
+} // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/stdfix/diviuk.h b/libc/src/stdfix/diviuk.h
new file mode 100644
index 0000000000000..4853e3206f969
--- /dev/null
+++ b/libc/src/stdfix/diviuk.h
@@ -0,0 +1,21 @@
+//===-- Implementation header for diviuk ------------------------*- C++ -*-===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_LIBC_SRC_STDFIX_DIVIUK_H
+#define LLVM_LIBC_SRC_STDFIX_DIVIUK_H
+
+#include "include/llvm-libc-macros/stdfix-macros.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+
+unsigned int diviuk(unsigned int n, unsigned accum d);
+
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SRC_STDFIX_DIVIUK_H
diff --git a/libc/src/stdfix/diviulk.cpp b/libc/src/stdfix/diviulk.cpp
new file mode 100644
index 0000000000000..2b66ffc0e4580
--- /dev/null
+++ b/libc/src/stdfix/diviulk.cpp
@@ -0,0 +1,22 @@
+//===-- Implementation of diviulk function --------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "diviulk.h"
+#include "include/llvm-libc-macros/stdfix-macros.h"
+#include "src/__support/common.h"
+#include "src/__support/fixed_point/fx_bits.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+
+LLVM_LIBC_FUNCTION(unsigned long int, diviulk,
+ (unsigned long int n, unsigned long accum d)) {
+ return fixed_point::divifx<unsigned long int, unsigned long accum>(n, d);
+}
+
+} // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/stdfix/diviulk.h b/libc/src/stdfix/diviulk.h
new file mode 100644
index 0000000000000..4c322ff84ba1f
--- /dev/null
+++ b/libc/src/stdfix/diviulk.h
@@ -0,0 +1,21 @@
+//===-- Implementation header for diviulk -----------------------*- C++ -*-===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_LIBC_SRC_STDFIX_DIVIULK_H
+#define LLVM_LIBC_SRC_STDFIX_DIVIULK_H
+
+#include "include/llvm-libc-macros/stdfix-macros.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+
+unsigned long int diviulk(unsigned long int n, unsigned long accum d);
+
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SRC_STDFIX_DIVIULK_H
diff --git a/libc/src/stdfix/diviulr.cpp b/libc/src/stdfix/diviulr.cpp
new file mode 100644
index 0000000000000..cb773d555e99d
--- /dev/null
+++ b/libc/src/stdfix/diviulr.cpp
@@ -0,0 +1,22 @@
+//===-- Implementation of diviulr function --------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "diviulr.h"
+#include "include/llvm-libc-macros/stdfix-macros.h"
+#include "src/__support/common.h"
+#include "src/__support/fixed_point/fx_bits.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+
+LLVM_LIBC_FUNCTION(unsigned long int, diviulr,
+ (unsigned long int n, unsigned long fract d)) {
+ return fixed_point::divifx<unsigned long int, unsigned long fract>(n, d);
+}
+
+} // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/stdfix/diviulr.h b/libc/src/stdfix/diviulr.h
new file mode 100644
index 0000000000000..8e15040294646
--- /dev/null
+++ b/libc/src/stdfix/diviulr.h
@@ -0,0 +1,21 @@
+//===-- Implementation header for diviulr -----------------------*- C++ -*-===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_LIBC_SRC_STDFIX_DIVIULR_H
+#define LLVM_LIBC_SRC_STDFIX_DIVIULR_H
+
+#include "include/llvm-libc-macros/stdfix-macros.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+
+unsigned long int diviulr(unsigned long int n, unsigned long fract d);
+
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SRC_STDFIX_DIVIULR_H
diff --git a/libc/src/stdfix/diviur.cpp b/libc/src/stdfix/diviur.cpp
new file mode 100644
index 0000000000000..252d1e381407d
--- /dev/null
+++ b/libc/src/stdfix/diviur.cpp
@@ -0,0 +1,21 @@
+//===-- Implementation of diviur function ---------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "diviur.h"
+#include "include/llvm-libc-macros/stdfix-macros.h"
+#include "src/__support/common.h"
+#include "src/__support/fixed_point/fx_bits.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+
+LLVM_LIBC_FUNCTION(unsigned int, diviur, (unsigned int n, unsigned fract d)) {
+ return fixed_point::divifx<unsigned int, unsigned fract>(n, d);
+}
+
+} // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/stdfix/diviur.h b/libc/src/stdfix/diviur.h
new file mode 100644
index 0000000000000..30651b942552a
--- /dev/null
+++ b/libc/src/stdfix/diviur.h
@@ -0,0 +1,21 @@
+//===-- Implementation header for diviur ------------------------*- C++ -*-===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_LIBC_SRC_STDFIX_DIVIUR_H
+#define LLVM_LIBC_SRC_STDFIX_DIVIUR_H
+
+#include "include/llvm-libc-macros/stdfix-macros.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+
+unsigned int diviur(unsigned int n, unsigned fract d);
+
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SRC_STDFIX_DIVIUR_H
diff --git a/libc/test/src/stdfix/CMakeLists.txt b/libc/test/src/stdfix/CMakeLists.txt
index b8fdb5845b6a8..8ebf69c66d66c 100644
--- a/libc/test/src/stdfix/CMakeLists.txt
+++ b/libc/test/src/stdfix/CMakeLists.txt
@@ -147,6 +147,23 @@ foreach(suffix IN ITEMS r)
)
endforeach()
+foreach(suffix IN ITEMS r lr k lk ur ulr uk ulk)
+ add_libc_test(
+ divi${suffix}_test
+ SUITE
+ libc-stdfix-tests
+ HDRS
+ DiviFxTest.h
+ SRCS
+ divi${suffix}_test.cpp
+ DEPENDS
+ libc.src.stdfix.divi${suffix}
+ libc.src.__support.fixed_point.fx_rep
+ libc.src.__support.fixed_point.fx_bits
+ libc.hdr.signal_macros
+ )
+endforeach()
+
add_libc_test(
uhksqrtus_test
SUITE
diff --git a/libc/test/src/stdfix/DiviFxTest.h b/libc/test/src/stdfix/DiviFxTest.h
new file mode 100644
index 0000000000000..06c4868367858
--- /dev/null
+++ b/libc/test/src/stdfix/DiviFxTest.h
@@ -0,0 +1,176 @@
+//===-- Utility class to test divifx functions ------------------*- C++ -*-===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "test/UnitTest/Test.h"
+
+#include "hdr/signal_macros.h"
+#include "llvm-libc-macros/stdfix-macros.h"
+#include "src/__support/CPP/limits.h"
+#include "src/__support/fixed_point/fx_bits.h"
+#include "src/__support/fixed_point/fx_rep.h"
+
+namespace cpp = LIBC_NAMESPACE::cpp;
+
+template <typename IntType, typename FXType>
+class DiviFxTest : public LIBC_NAMESPACE::testing::Test {
+
+ using FXRep = LIBC_NAMESPACE::fixed_point::FXRep<FXType>;
+
+ static constexpr FXType max = FXRep::MAX();
+ static constexpr FXType min = FXRep::MIN();
+ static constexpr FXType zero = FXRep::ZERO();
+ static constexpr FXType epsilon = FXRep::EPS();
+ static constexpr FXType one_half = FXRep::ONE_HALF();
+ static constexpr FXType one_fourth = FXRep::ONE_FOURTH();
+ static constexpr FXType one_eighth = FXRep::ONE_EIGHTH();
+
+ static constexpr bool is_signed = (FXRep::SIGN_LEN > 0);
+ static constexpr bool has_integral = (FXRep::INTEGRAL_LEN > 0);
+
+public:
+ typedef IntType (*DiviFxFunc)(IntType, FXType);
+
+ void testBasicNumbers(DiviFxFunc func) {
+
+ EXPECT_EQ(func(0, one_eighth), static_cast<IntType>(0));
+ EXPECT_EQ(func(0, one_fourth), static_cast<IntType>(0));
+ EXPECT_EQ(func(0, one_half), static_cast<IntType>(0));
+ EXPECT_EQ(func(1, one_eighth), static_cast<IntType>(8));
+ EXPECT_EQ(func(1, one_fourth), static_cast<IntType>(4));
+ EXPECT_EQ(func(1, one_half), static_cast<IntType>(2));
+ EXPECT_EQ(func(2, one_eighth), static_cast<IntType>(16));
+ EXPECT_EQ(func(2, one_fourth), static_cast<IntType>(8));
+ EXPECT_EQ(func(2, one_half), static_cast<IntType>(4));
+
+ // Verify rounding towards 0.
+ EXPECT_EQ(func(1, 3 * one_fourth), static_cast<IntType>(1));
+ EXPECT_EQ(func(2, 3 * one_fourth), static_cast<IntType>(2));
+
+ if constexpr (is_signed) {
+ EXPECT_EQ(func(-1, one_half), static_cast<IntType>(-2));
+ EXPECT_EQ(func(1, -one_half), static_cast<IntType>(-2));
+ EXPECT_EQ(func(-1, -one_half), static_cast<IntType>(2));
+ EXPECT_EQ(func(-2, one_fourth), static_cast<IntType>(-8));
+ EXPECT_EQ(func(2, -one_fourth), static_cast<IntType>(-8));
+
+ // Verify rounding towards 0.
+ EXPECT_EQ(func(-1, 3 * one_fourth), static_cast<IntType>(-1));
+ EXPECT_EQ(func(1, -3 * one_fourth), static_cast<IntType>(-1));
+ EXPECT_EQ(func(-2, 3 * one_fourth), static_cast<IntType>(-2));
+ EXPECT_EQ(func(2, -3 * one_fourth), static_cast<IntType>(-2));
+
+ EXPECT_EQ(func(1, static_cast<FXType>(-1)), static_cast<IntType>(-1));
+ EXPECT_EQ(func(-1, static_cast<FXType>(-1)), static_cast<IntType>(1));
+ }
+
+ if constexpr (has_integral) {
+ EXPECT_EQ(func(1, static_cast<FXType>(1)), static_cast<IntType>(1));
+
+ if constexpr (is_signed) {
+ EXPECT_EQ(func(-1, static_cast<FXType>(1)), static_cast<IntType>(-1));
+ }
+
+ // Only run these tests for accum types that can represent these operands.
+ constexpr FXType max_test_operand = static_cast<FXType>(4);
+
+ if constexpr (max >= max_test_operand) {
+ EXPECT_EQ(func(3, 2.5), static_cast<IntType>(1));
+ EXPECT_EQ(func(2, 3.5), static_cast<IntType>(0));
+ EXPECT_EQ(func(3, 1.5), static_cast<IntType>(2));
+ EXPECT_EQ(func(4, 2.0), static_cast<IntType>(2));
+
+ if constexpr (is_signed) {
+ EXPECT_EQ(func(2, -3.5), static_cast<IntType>(0));
+ EXPECT_EQ(func(-3, 2.5), static_cast<IntType>(-1));
+ EXPECT_EQ(func(-3, 1.5), static_cast<IntType>(-2));
+ EXPECT_EQ(func(-3, -2.5), static_cast<IntType>(1));
+ }
+ }
+ }
+ }
+
+ void testEdgeCases(DiviFxFunc func) {
+
+ constexpr IntType int_max = cpp::numeric_limits<IntType>::max();
+
+ if constexpr (has_integral) {
+ EXPECT_EQ(func(int_max, static_cast<FXType>(1)), int_max);
+ }
+
+ if constexpr (is_signed) {
+ EXPECT_EQ(func(int_max, static_cast<FXType>(-1)), -int_max);
+ }
+
+ // Only valid when integral bits (excluding sign) exceed fraction bits.
+ // Otherwise 1<<FRACTION_LEN may not fit in IntType.
+ if constexpr ((FXRep::INTEGRAL_LEN) > FXRep::FRACTION_LEN) {
+ constexpr IntType epsilon_result = static_cast<IntType>(1)
+ << FXRep::FRACTION_LEN;
+ EXPECT_EQ(func(1, epsilon), epsilon_result);
+ if constexpr (is_signed) {
+ EXPECT_EQ(func(1, -epsilon), -epsilon_result);
+ EXPECT_EQ(func(-1, epsilon), -epsilon_result);
+ EXPECT_EQ(func(-1, -epsilon), epsilon_result);
+ }
+ }
+
+ if constexpr (has_integral) {
+ constexpr IntType largest_positive =
+ ((static_cast<IntType>(1) << FXRep::INTEGRAL_LEN) - 1);
+ EXPECT_EQ(func(largest_positive, static_cast<FXType>(largest_positive)),
+ static_cast<IntType>(1));
+
+ constexpr IntType largest_power_of_two = static_cast<IntType>(1)
+ << (FXRep::INTEGRAL_LEN - 1);
+ EXPECT_EQ(
+ func(largest_power_of_two, static_cast<FXType>(largest_power_of_two)),
+ static_cast<IntType>(1));
+ }
+
+ if constexpr (!has_integral) {
+ EXPECT_EQ(func(1, max), static_cast<IntType>(1));
+
+ if constexpr (is_signed) {
+ EXPECT_EQ(func(1, min), static_cast<IntType>(-1));
+ }
+ }
+
+ if constexpr (has_integral) {
+ EXPECT_EQ(func(1, max), static_cast<IntType>(0));
+
+ if constexpr (is_signed) {
+ EXPECT_EQ(func(1, min), static_cast<IntType>(0));
+ }
+ }
+ }
+
+ void testInvalidNumbers(DiviFxFunc func) {
+
+ EXPECT_DEATH([func] { func(1, zero); }, WITH_SIGNAL(-1));
+ if constexpr (has_integral) {
+ EXPECT_DEATH([func] { func(2, zero); }, WITH_SIGNAL(-1));
+ }
+ }
+};
+
+#if defined(LIBC_ADD_NULL_CHECKS)
+#define LIST_DIVIFX_TESTS(Name, IntType, FXType, func) \
+ using LlvmLibcDivi##Name##Test = DiviFxTest<IntType, FXType>; \
+ TEST_F(LlvmLibcDivi##Name##Test, InvalidNumbers) { \
+ testInvalidNumbers(&func); \
+ } \
+ TEST_F(LlvmLibcDivi##Name##Test, BasicNumbers) { testBasicNumbers(&func); } \
+ TEST_F(LlvmLibcDivi##Name##Test, EdgeCases) { testEdgeCases(&func); } \
+ static_assert(true, "Require semicolon.")
+#else
+#define LIST_DIVIFX_TESTS(Name, IntType, FXType, func) \
+ using LlvmLibcDivi##Name##Test = DiviFxTest<IntType, FXType>; \
+ TEST_F(LlvmLibcDivi##Name##Test, BasicNumbers) { testBasicNumbers(&func); } \
+ TEST_F(LlvmLibcDivi##Name##Test, EdgeCases) { testEdgeCases(&func); } \
+ static_assert(true, "Require semicolon.")
+#endif // LIBC_ADD_NULL_CHECKS
diff --git a/libc/test/src/stdfix/divik_test.cpp b/libc/test/src/stdfix/divik_test.cpp
new file mode 100644
index 0000000000000..1287d5d1a8d48
--- /dev/null
+++ b/libc/test/src/stdfix/divik_test.cpp
@@ -0,0 +1,14 @@
+//===-- Unittests for divik -----------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "DiviFxTest.h"
+
+#include "llvm-libc-macros/stdfix-macros.h"
+#include "src/stdfix/divik.h"
+
+LIST_DIVIFX_TESTS(k, int, accum, LIBC_NAMESPACE::divik);
diff --git a/libc/test/src/stdfix/divilk_test.cpp b/libc/test/src/stdfix/divilk_test.cpp
new file mode 100644
index 0000000000000..ebc6941139ca7
--- /dev/null
+++ b/libc/test/src/stdfix/divilk_test.cpp
@@ -0,0 +1,14 @@
+//===-- Unittests for divilk ----------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "DiviFxTest.h"
+
+#include "llvm-libc-macros/stdfix-macros.h"
+#include "src/stdfix/divilk.h"
+
+LIST_DIVIFX_TESTS(lk, long int, long accum, LIBC_NAMESPACE::divilk);
diff --git a/libc/test/src/stdfix/divilr_test.cpp b/libc/test/src/stdfix/divilr_test.cpp
new file mode 100644
index 0000000000000..99567836f27b6
--- /dev/null
+++ b/libc/test/src/stdfix/divilr_test.cpp
@@ -0,0 +1,14 @@
+//===-- Unittests for divilr ----------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "DiviFxTest.h"
+
+#include "llvm-libc-macros/stdfix-macros.h"
+#include "src/stdfix/divilr.h"
+
+LIST_DIVIFX_TESTS(lr, long int, long fract, LIBC_NAMESPACE::divilr);
diff --git a/libc/test/src/stdfix/divir_test.cpp b/libc/test/src/stdfix/divir_test.cpp
new file mode 100644
index 0000000000000..e8b055561014b
--- /dev/null
+++ b/libc/test/src/stdfix/divir_test.cpp
@@ -0,0 +1,14 @@
+//===-- Unittests for divir -----------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "DiviFxTest.h"
+
+#include "llvm-libc-macros/stdfix-macros.h"
+#include "src/stdfix/divir.h"
+
+LIST_DIVIFX_TESTS(r, int, fract, LIBC_NAMESPACE::divir);
diff --git a/libc/test/src/stdfix/diviuk_test.cpp b/libc/test/src/stdfix/diviuk_test.cpp
new file mode 100644
index 0000000000000..a7d632a661502
--- /dev/null
+++ b/libc/test/src/stdfix/diviuk_test.cpp
@@ -0,0 +1,14 @@
+//===-- Unittests for diviuk ----------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "DiviFxTest.h"
+
+#include "llvm-libc-macros/stdfix-macros.h"
+#include "src/stdfix/diviuk.h"
+
+LIST_DIVIFX_TESTS(uk, unsigned int, unsigned accum, LIBC_NAMESPACE::diviuk);
diff --git a/libc/test/src/stdfix/diviulk_test.cpp b/libc/test/src/stdfix/diviulk_test.cpp
new file mode 100644
index 0000000000000..4709e5728fe32
--- /dev/null
+++ b/libc/test/src/stdfix/diviulk_test.cpp
@@ -0,0 +1,15 @@
+//===-- Unittests for diviulk ---------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "DiviFxTest.h"
+
+#include "llvm-libc-macros/stdfix-macros.h"
+#include "src/stdfix/diviulk.h"
+
+LIST_DIVIFX_TESTS(ulk, unsigned long int, unsigned long accum,
+ LIBC_NAMESPACE::diviulk);
diff --git a/libc/test/src/stdfix/diviulr_test.cpp b/libc/test/src/stdfix/diviulr_test.cpp
new file mode 100644
index 0000000000000..48cc1f288c919
--- /dev/null
+++ b/libc/test/src/stdfix/diviulr_test.cpp
@@ -0,0 +1,15 @@
+//===-- Unittests for diviulr ---------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "DiviFxTest.h"
+
+#include "llvm-libc-macros/stdfix-macros.h"
+#include "src/stdfix/diviulr.h"
+
+LIST_DIVIFX_TESTS(ulr, unsigned long int, unsigned long fract,
+ LIBC_NAMESPACE::diviulr);
diff --git a/libc/test/src/stdfix/diviur_test.cpp b/libc/test/src/stdfix/diviur_test.cpp
new file mode 100644
index 0000000000000..6fd1c17d3cd10
--- /dev/null
+++ b/libc/test/src/stdfix/diviur_test.cpp
@@ -0,0 +1,14 @@
+//===-- Unittests for diviur ----------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "DiviFxTest.h"
+
+#include "llvm-libc-macros/stdfix-macros.h"
+#include "src/stdfix/diviur.h"
+
+LIST_DIVIFX_TESTS(ur, unsigned int, unsigned fract, LIBC_NAMESPACE::diviur);
More information about the libc-commits
mailing list