[libc-commits] [libc] [llvm] [libc][math] Refactor round-roundeven-trunc family to header-only (PR #195590)

via libc-commits libc-commits at lists.llvm.org
Mon May 4 00:14:23 PDT 2026


https://github.com/AnonMiraj updated https://github.com/llvm/llvm-project/pull/195590

>From b5947a70e18e24ddf850b08736d621af772de82e Mon Sep 17 00:00:00 2001
From: Anonmiraj <ezzibrahimx at gmail.com>
Date: Mon, 4 May 2026 09:23:03 +0300
Subject: [PATCH 1/5] [libc][math] Refactor round-roundeven-trunc family to
 header-only

Refactored functions:
  - round
  - roundbf16
  - roundf
  - roundf128
  - roundf16
  - roundl
  - roundeven
  - roundevenbf16
  - roundevenf
  - roundevenf128
  - roundevenf16
  - roundevenl
  - trunc
  - truncbf16
  - truncf
  - truncf128
  - truncf16
  - truncl
---
 libc/shared/math.h                            |  18 ++
 libc/shared/math/round.h                      |  23 ++
 libc/shared/math/roundbf16.h                  |  23 ++
 libc/shared/math/roundeven.h                  |  23 ++
 libc/shared/math/roundevenbf16.h              |  23 ++
 libc/shared/math/roundevenf.h                 |  23 ++
 libc/shared/math/roundevenf128.h              |  29 ++
 libc/shared/math/roundevenf16.h               |  29 ++
 libc/shared/math/roundevenl.h                 |  23 ++
 libc/shared/math/roundf.h                     |  23 ++
 libc/shared/math/roundf128.h                  |  29 ++
 libc/shared/math/roundf16.h                   |  29 ++
 libc/shared/math/roundl.h                     |  23 ++
 libc/shared/math/trunc.h                      |  23 ++
 libc/shared/math/truncbf16.h                  |  23 ++
 libc/shared/math/truncf.h                     |  23 ++
 libc/shared/math/truncf128.h                  |  29 ++
 libc/shared/math/truncf16.h                   |  29 ++
 libc/shared/math/truncl.h                     |  23 ++
 libc/src/__support/math/CMakeLists.txt        | 199 +++++++++++++
 libc/src/__support/math/round.h               |  29 ++
 libc/src/__support/math/roundbf16.h           |  26 ++
 libc/src/__support/math/roundeven.h           |  30 ++
 libc/src/__support/math/roundevenbf16.h       |  26 ++
 libc/src/__support/math/roundevenf.h          |  30 ++
 libc/src/__support/math/roundevenf128.h       |  31 ++
 libc/src/__support/math/roundevenf16.h        |  39 +++
 libc/src/__support/math/roundevenl.h          |  25 ++
 libc/src/__support/math/roundf.h              |  29 ++
 libc/src/__support/math/roundf128.h           |  31 ++
 libc/src/__support/math/roundf16.h            |  39 +++
 libc/src/__support/math/roundl.h              |  25 ++
 libc/src/__support/math/trunc.h               |  30 ++
 libc/src/__support/math/truncbf16.h           |  26 ++
 libc/src/__support/math/truncf.h              |  30 ++
 libc/src/__support/math/truncf128.h           |  31 ++
 libc/src/__support/math/truncf16.h            |  39 +++
 libc/src/__support/math/truncl.h              |  25 ++
 libc/src/math/generic/CMakeLists.txt          |  84 ++----
 libc/src/math/generic/round.cpp               |  12 +-
 libc/src/math/generic/roundbf16.cpp           |   7 +-
 libc/src/math/generic/roundeven.cpp           |  12 +-
 libc/src/math/generic/roundevenbf16.cpp       |   7 +-
 libc/src/math/generic/roundevenf.cpp          |  12 +-
 libc/src/math/generic/roundevenf128.cpp       |   6 +-
 libc/src/math/generic/roundevenf16.cpp        |  13 +-
 libc/src/math/generic/roundevenl.cpp          |   6 +-
 libc/src/math/generic/roundf.cpp              |  12 +-
 libc/src/math/generic/roundf128.cpp           |   6 +-
 libc/src/math/generic/roundf16.cpp            |  15 +-
 libc/src/math/generic/roundl.cpp              |   6 +-
 libc/src/math/generic/trunc.cpp               |  12 +-
 libc/src/math/generic/truncbf16.cpp           |   7 +-
 libc/src/math/generic/truncf.cpp              |  12 +-
 libc/src/math/generic/truncf128.cpp           |   6 +-
 libc/src/math/generic/truncf16.cpp            |  15 +-
 libc/src/math/generic/truncl.cpp              |   6 +-
 libc/test/shared/CMakeLists.txt               |  36 +++
 .../shared/shared_math_constexpr_test.cpp     |  24 ++
 libc/test/shared/shared_math_test.cpp         |  20 ++
 .../llvm-project-overlay/libc/BUILD.bazel     | 276 +++++++++++++++++-
 61 files changed, 1603 insertions(+), 217 deletions(-)
 create mode 100644 libc/shared/math/round.h
 create mode 100644 libc/shared/math/roundbf16.h
 create mode 100644 libc/shared/math/roundeven.h
 create mode 100644 libc/shared/math/roundevenbf16.h
 create mode 100644 libc/shared/math/roundevenf.h
 create mode 100644 libc/shared/math/roundevenf128.h
 create mode 100644 libc/shared/math/roundevenf16.h
 create mode 100644 libc/shared/math/roundevenl.h
 create mode 100644 libc/shared/math/roundf.h
 create mode 100644 libc/shared/math/roundf128.h
 create mode 100644 libc/shared/math/roundf16.h
 create mode 100644 libc/shared/math/roundl.h
 create mode 100644 libc/shared/math/trunc.h
 create mode 100644 libc/shared/math/truncbf16.h
 create mode 100644 libc/shared/math/truncf.h
 create mode 100644 libc/shared/math/truncf128.h
 create mode 100644 libc/shared/math/truncf16.h
 create mode 100644 libc/shared/math/truncl.h
 create mode 100644 libc/src/__support/math/round.h
 create mode 100644 libc/src/__support/math/roundbf16.h
 create mode 100644 libc/src/__support/math/roundeven.h
 create mode 100644 libc/src/__support/math/roundevenbf16.h
 create mode 100644 libc/src/__support/math/roundevenf.h
 create mode 100644 libc/src/__support/math/roundevenf128.h
 create mode 100644 libc/src/__support/math/roundevenf16.h
 create mode 100644 libc/src/__support/math/roundevenl.h
 create mode 100644 libc/src/__support/math/roundf.h
 create mode 100644 libc/src/__support/math/roundf128.h
 create mode 100644 libc/src/__support/math/roundf16.h
 create mode 100644 libc/src/__support/math/roundl.h
 create mode 100644 libc/src/__support/math/trunc.h
 create mode 100644 libc/src/__support/math/truncbf16.h
 create mode 100644 libc/src/__support/math/truncf.h
 create mode 100644 libc/src/__support/math/truncf128.h
 create mode 100644 libc/src/__support/math/truncf16.h
 create mode 100644 libc/src/__support/math/truncl.h

diff --git a/libc/shared/math.h b/libc/shared/math.h
index a3cdbb12f0e51..746f5270d8c84 100644
--- a/libc/shared/math.h
+++ b/libc/shared/math.h
@@ -410,6 +410,18 @@
 #include "math/rintf128.h"
 #include "math/rintf16.h"
 #include "math/rintl.h"
+#include "math/round.h"
+#include "math/roundbf16.h"
+#include "math/roundeven.h"
+#include "math/roundevenbf16.h"
+#include "math/roundevenf.h"
+#include "math/roundevenf128.h"
+#include "math/roundevenf16.h"
+#include "math/roundevenl.h"
+#include "math/roundf.h"
+#include "math/roundf128.h"
+#include "math/roundf16.h"
+#include "math/roundl.h"
 #include "math/rsqrtf.h"
 #include "math/rsqrtf16.h"
 #include "math/scalbln.h"
@@ -470,6 +482,12 @@
 #include "math/totalordermagf128.h"
 #include "math/totalordermagf16.h"
 #include "math/totalordermagl.h"
+#include "math/trunc.h"
+#include "math/truncbf16.h"
+#include "math/truncf.h"
+#include "math/truncf128.h"
+#include "math/truncf16.h"
+#include "math/truncl.h"
 #include "math/ufromfp.h"
 #include "math/ufromfpbf16.h"
 #include "math/ufromfpf.h"
diff --git a/libc/shared/math/round.h b/libc/shared/math/round.h
new file mode 100644
index 0000000000000..74282f8830527
--- /dev/null
+++ b/libc/shared/math/round.h
@@ -0,0 +1,23 @@
+//===-- Shared round function -----------------------------------*- 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_SHARED_MATH_ROUND_H
+#define LLVM_LIBC_SHARED_MATH_ROUND_H
+
+#include "shared/libc_common.h"
+#include "src/__support/math/round.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace shared {
+
+using math::round;
+
+} // namespace shared
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SHARED_MATH_ROUND_H
diff --git a/libc/shared/math/roundbf16.h b/libc/shared/math/roundbf16.h
new file mode 100644
index 0000000000000..565fa6bc52df9
--- /dev/null
+++ b/libc/shared/math/roundbf16.h
@@ -0,0 +1,23 @@
+//===-- Shared roundbf16 function -------------------------------*- 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_SHARED_MATH_ROUNDBF16_H
+#define LLVM_LIBC_SHARED_MATH_ROUNDBF16_H
+
+#include "shared/libc_common.h"
+#include "src/__support/math/roundbf16.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace shared {
+
+using math::roundbf16;
+
+} // namespace shared
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SHARED_MATH_ROUNDBF16_H
diff --git a/libc/shared/math/roundeven.h b/libc/shared/math/roundeven.h
new file mode 100644
index 0000000000000..42a3533e80511
--- /dev/null
+++ b/libc/shared/math/roundeven.h
@@ -0,0 +1,23 @@
+//===-- Shared roundeven function -------------------------------*- 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_SHARED_MATH_ROUNDEVEN_H
+#define LLVM_LIBC_SHARED_MATH_ROUNDEVEN_H
+
+#include "shared/libc_common.h"
+#include "src/__support/math/roundeven.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace shared {
+
+using math::roundeven;
+
+} // namespace shared
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SHARED_MATH_ROUNDEVEN_H
diff --git a/libc/shared/math/roundevenbf16.h b/libc/shared/math/roundevenbf16.h
new file mode 100644
index 0000000000000..7d1d93600b437
--- /dev/null
+++ b/libc/shared/math/roundevenbf16.h
@@ -0,0 +1,23 @@
+//===-- Shared roundevenbf16 function ---------------------------*- 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_SHARED_MATH_ROUNDEVENBF16_H
+#define LLVM_LIBC_SHARED_MATH_ROUNDEVENBF16_H
+
+#include "shared/libc_common.h"
+#include "src/__support/math/roundevenbf16.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace shared {
+
+using math::roundevenbf16;
+
+} // namespace shared
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SHARED_MATH_ROUNDEVENBF16_H
diff --git a/libc/shared/math/roundevenf.h b/libc/shared/math/roundevenf.h
new file mode 100644
index 0000000000000..bec33017bee5b
--- /dev/null
+++ b/libc/shared/math/roundevenf.h
@@ -0,0 +1,23 @@
+//===-- Shared roundevenf function ------------------------------*- 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_SHARED_MATH_ROUNDEVENF_H
+#define LLVM_LIBC_SHARED_MATH_ROUNDEVENF_H
+
+#include "shared/libc_common.h"
+#include "src/__support/math/roundevenf.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace shared {
+
+using math::roundevenf;
+
+} // namespace shared
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SHARED_MATH_ROUNDEVENF_H
diff --git a/libc/shared/math/roundevenf128.h b/libc/shared/math/roundevenf128.h
new file mode 100644
index 0000000000000..5d47fd5d267f8
--- /dev/null
+++ b/libc/shared/math/roundevenf128.h
@@ -0,0 +1,29 @@
+//===-- Shared roundevenf128 function ---------------------------*- 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_SHARED_MATH_ROUNDEVENF128_H
+#define LLVM_LIBC_SHARED_MATH_ROUNDEVENF128_H
+
+#include "include/llvm-libc-types/float128.h"
+
+#ifdef LIBC_TYPES_HAS_FLOAT128
+
+#include "shared/libc_common.h"
+#include "src/__support/math/roundevenf128.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace shared {
+
+using math::roundevenf128;
+
+} // namespace shared
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LIBC_TYPES_HAS_FLOAT128
+
+#endif // LLVM_LIBC_SHARED_MATH_ROUNDEVENF128_H
diff --git a/libc/shared/math/roundevenf16.h b/libc/shared/math/roundevenf16.h
new file mode 100644
index 0000000000000..fbe287471ed59
--- /dev/null
+++ b/libc/shared/math/roundevenf16.h
@@ -0,0 +1,29 @@
+//===-- Shared roundevenf16 function ----------------------------*- 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_SHARED_MATH_ROUNDEVENF16_H
+#define LLVM_LIBC_SHARED_MATH_ROUNDEVENF16_H
+
+#include "include/llvm-libc-macros/float16-macros.h"
+
+#ifdef LIBC_TYPES_HAS_FLOAT16
+
+#include "shared/libc_common.h"
+#include "src/__support/math/roundevenf16.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace shared {
+
+using math::roundevenf16;
+
+} // namespace shared
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LIBC_TYPES_HAS_FLOAT16
+
+#endif // LLVM_LIBC_SHARED_MATH_ROUNDEVENF16_H
diff --git a/libc/shared/math/roundevenl.h b/libc/shared/math/roundevenl.h
new file mode 100644
index 0000000000000..b8beb858a0cc0
--- /dev/null
+++ b/libc/shared/math/roundevenl.h
@@ -0,0 +1,23 @@
+//===-- Shared roundevenl function ------------------------------*- 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_SHARED_MATH_ROUNDEVENL_H
+#define LLVM_LIBC_SHARED_MATH_ROUNDEVENL_H
+
+#include "shared/libc_common.h"
+#include "src/__support/math/roundevenl.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace shared {
+
+using math::roundevenl;
+
+} // namespace shared
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SHARED_MATH_ROUNDEVENL_H
diff --git a/libc/shared/math/roundf.h b/libc/shared/math/roundf.h
new file mode 100644
index 0000000000000..5822fe2d37346
--- /dev/null
+++ b/libc/shared/math/roundf.h
@@ -0,0 +1,23 @@
+//===-- Shared roundf function ----------------------------------*- 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_SHARED_MATH_ROUNDF_H
+#define LLVM_LIBC_SHARED_MATH_ROUNDF_H
+
+#include "shared/libc_common.h"
+#include "src/__support/math/roundf.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace shared {
+
+using math::roundf;
+
+} // namespace shared
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SHARED_MATH_ROUNDF_H
diff --git a/libc/shared/math/roundf128.h b/libc/shared/math/roundf128.h
new file mode 100644
index 0000000000000..ea0fd23fce180
--- /dev/null
+++ b/libc/shared/math/roundf128.h
@@ -0,0 +1,29 @@
+//===-- Shared roundf128 function -------------------------------*- 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_SHARED_MATH_ROUNDF128_H
+#define LLVM_LIBC_SHARED_MATH_ROUNDF128_H
+
+#include "include/llvm-libc-types/float128.h"
+
+#ifdef LIBC_TYPES_HAS_FLOAT128
+
+#include "shared/libc_common.h"
+#include "src/__support/math/roundf128.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace shared {
+
+using math::roundf128;
+
+} // namespace shared
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LIBC_TYPES_HAS_FLOAT128
+
+#endif // LLVM_LIBC_SHARED_MATH_ROUNDF128_H
diff --git a/libc/shared/math/roundf16.h b/libc/shared/math/roundf16.h
new file mode 100644
index 0000000000000..d097cba753f0f
--- /dev/null
+++ b/libc/shared/math/roundf16.h
@@ -0,0 +1,29 @@
+//===-- Shared roundf16 function --------------------------------*- 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_SHARED_MATH_ROUNDF16_H
+#define LLVM_LIBC_SHARED_MATH_ROUNDF16_H
+
+#include "include/llvm-libc-macros/float16-macros.h"
+
+#ifdef LIBC_TYPES_HAS_FLOAT16
+
+#include "shared/libc_common.h"
+#include "src/__support/math/roundf16.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace shared {
+
+using math::roundf16;
+
+} // namespace shared
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LIBC_TYPES_HAS_FLOAT16
+
+#endif // LLVM_LIBC_SHARED_MATH_ROUNDF16_H
diff --git a/libc/shared/math/roundl.h b/libc/shared/math/roundl.h
new file mode 100644
index 0000000000000..644f7f17fae5d
--- /dev/null
+++ b/libc/shared/math/roundl.h
@@ -0,0 +1,23 @@
+//===-- Shared roundl function ----------------------------------*- 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_SHARED_MATH_ROUNDL_H
+#define LLVM_LIBC_SHARED_MATH_ROUNDL_H
+
+#include "shared/libc_common.h"
+#include "src/__support/math/roundl.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace shared {
+
+using math::roundl;
+
+} // namespace shared
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SHARED_MATH_ROUNDL_H
diff --git a/libc/shared/math/trunc.h b/libc/shared/math/trunc.h
new file mode 100644
index 0000000000000..06e2aefe8164d
--- /dev/null
+++ b/libc/shared/math/trunc.h
@@ -0,0 +1,23 @@
+//===-- Shared trunc function -----------------------------------*- 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_SHARED_MATH_TRUNC_H
+#define LLVM_LIBC_SHARED_MATH_TRUNC_H
+
+#include "shared/libc_common.h"
+#include "src/__support/math/trunc.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace shared {
+
+using math::trunc;
+
+} // namespace shared
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SHARED_MATH_TRUNC_H
diff --git a/libc/shared/math/truncbf16.h b/libc/shared/math/truncbf16.h
new file mode 100644
index 0000000000000..1e5c6e96f215a
--- /dev/null
+++ b/libc/shared/math/truncbf16.h
@@ -0,0 +1,23 @@
+//===-- Shared truncbf16 function -------------------------------*- 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_SHARED_MATH_TRUNCBF16_H
+#define LLVM_LIBC_SHARED_MATH_TRUNCBF16_H
+
+#include "shared/libc_common.h"
+#include "src/__support/math/truncbf16.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace shared {
+
+using math::truncbf16;
+
+} // namespace shared
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SHARED_MATH_TRUNCBF16_H
diff --git a/libc/shared/math/truncf.h b/libc/shared/math/truncf.h
new file mode 100644
index 0000000000000..63f70770aff2a
--- /dev/null
+++ b/libc/shared/math/truncf.h
@@ -0,0 +1,23 @@
+//===-- Shared truncf function ----------------------------------*- 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_SHARED_MATH_TRUNCF_H
+#define LLVM_LIBC_SHARED_MATH_TRUNCF_H
+
+#include "shared/libc_common.h"
+#include "src/__support/math/truncf.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace shared {
+
+using math::truncf;
+
+} // namespace shared
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SHARED_MATH_TRUNCF_H
diff --git a/libc/shared/math/truncf128.h b/libc/shared/math/truncf128.h
new file mode 100644
index 0000000000000..7694a8e4955e8
--- /dev/null
+++ b/libc/shared/math/truncf128.h
@@ -0,0 +1,29 @@
+//===-- Shared truncf128 function -------------------------------*- 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_SHARED_MATH_TRUNCF128_H
+#define LLVM_LIBC_SHARED_MATH_TRUNCF128_H
+
+#include "include/llvm-libc-types/float128.h"
+
+#ifdef LIBC_TYPES_HAS_FLOAT128
+
+#include "shared/libc_common.h"
+#include "src/__support/math/truncf128.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace shared {
+
+using math::truncf128;
+
+} // namespace shared
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LIBC_TYPES_HAS_FLOAT128
+
+#endif // LLVM_LIBC_SHARED_MATH_TRUNCF128_H
diff --git a/libc/shared/math/truncf16.h b/libc/shared/math/truncf16.h
new file mode 100644
index 0000000000000..8f5126d87e603
--- /dev/null
+++ b/libc/shared/math/truncf16.h
@@ -0,0 +1,29 @@
+//===-- Shared truncf16 function --------------------------------*- 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_SHARED_MATH_TRUNCF16_H
+#define LLVM_LIBC_SHARED_MATH_TRUNCF16_H
+
+#include "include/llvm-libc-macros/float16-macros.h"
+
+#ifdef LIBC_TYPES_HAS_FLOAT16
+
+#include "shared/libc_common.h"
+#include "src/__support/math/truncf16.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace shared {
+
+using math::truncf16;
+
+} // namespace shared
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LIBC_TYPES_HAS_FLOAT16
+
+#endif // LLVM_LIBC_SHARED_MATH_TRUNCF16_H
diff --git a/libc/shared/math/truncl.h b/libc/shared/math/truncl.h
new file mode 100644
index 0000000000000..4b5760936fb96
--- /dev/null
+++ b/libc/shared/math/truncl.h
@@ -0,0 +1,23 @@
+//===-- Shared truncl function ----------------------------------*- 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_SHARED_MATH_TRUNCL_H
+#define LLVM_LIBC_SHARED_MATH_TRUNCL_H
+
+#include "shared/libc_common.h"
+#include "src/__support/math/truncl.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace shared {
+
+using math::truncl;
+
+} // namespace shared
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SHARED_MATH_TRUNCL_H
diff --git a/libc/src/__support/math/CMakeLists.txt b/libc/src/__support/math/CMakeLists.txt
index fb0ecec031c75..dd27e70b903d3 100644
--- a/libc/src/__support/math/CMakeLists.txt
+++ b/libc/src/__support/math/CMakeLists.txt
@@ -2368,6 +2368,138 @@ add_header_library(
     libc.src.__support.macros.config
 )
 
+add_header_library(
+  round
+  HDRS
+    round.h
+  DEPENDS
+    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.macros.config
+  FLAGS
+    ROUND_OPT
+)
+
+add_header_library(
+  roundbf16
+  HDRS
+    roundbf16.h
+  DEPENDS
+    libc.src.__support.FPUtil.bfloat16
+    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.macros.config
+  FLAGS
+    ROUND_OPT
+)
+add_header_library(
+  roundeven
+  HDRS
+    roundeven.h
+  DEPENDS
+    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.macros.config
+  FLAGS
+    ROUND_OPT
+)
+
+add_header_library(
+  roundevenbf16
+  HDRS
+    roundevenbf16.h
+  DEPENDS
+    libc.src.__support.FPUtil.bfloat16
+    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.macros.config
+  FLAGS
+    ROUND_OPT
+)
+
+add_header_library(
+  roundevenf
+  HDRS
+    roundevenf.h
+  DEPENDS
+    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.macros.config
+  FLAGS
+    ROUND_OPT
+)
+
+add_header_library(
+  roundevenf128
+  HDRS
+    roundevenf128.h
+  DEPENDS
+    libc.include.llvm-libc-types.float128
+    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.macros.config
+)
+
+add_header_library(
+  roundevenf16
+  HDRS
+    roundevenf16.h
+  DEPENDS
+    libc.include.llvm-libc-macros.float16_macros
+    libc.src.__support.FPUtil.cast
+    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.macros.config
+  FLAGS
+    ROUND_OPT
+)
+
+add_header_library(
+  roundevenl
+  HDRS
+    roundevenl.h
+  DEPENDS
+    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.macros.config
+)
+
+
+add_header_library(
+  roundf
+  HDRS
+    roundf.h
+  DEPENDS
+    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.macros.config
+  FLAGS
+    ROUND_OPT
+)
+
+add_header_library(
+  roundf128
+  HDRS
+    roundf128.h
+  DEPENDS
+    libc.include.llvm-libc-types.float128
+    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.macros.config
+)
+
+add_header_library(
+  roundf16
+  HDRS
+    roundf16.h
+  DEPENDS
+    libc.include.llvm-libc-macros.float16_macros
+    libc.src.__support.FPUtil.cast
+    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.macros.config
+  FLAGS
+    ROUND_OPT
+)
+
+add_header_library(
+  roundl
+  HDRS
+    roundl.h
+  DEPENDS
+    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.macros.config
+)
+
 add_header_library(
   scalbln
   HDRS
@@ -5396,6 +5528,73 @@ add_header_library(
     libc.src.__support.macros.config
 )
 
+add_header_library(
+  trunc
+  HDRS
+    trunc.h
+  DEPENDS
+    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.macros.config
+  FLAGS
+    ROUND_OPT
+)
+
+add_header_library(
+  truncbf16
+  HDRS
+    truncbf16.h
+  DEPENDS
+    libc.src.__support.FPUtil.bfloat16
+    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.macros.config
+  FLAGS
+    ROUND_OPT
+)
+
+add_header_library(
+  truncf
+  HDRS
+    truncf.h
+  DEPENDS
+    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.macros.config
+  FLAGS
+    ROUND_OPT
+)
+
+add_header_library(
+  truncf128
+  HDRS
+    truncf128.h
+  DEPENDS
+    libc.include.llvm-libc-types.float128
+    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.macros.config
+)
+
+add_header_library(
+  truncf16
+  HDRS
+    truncf16.h
+  DEPENDS
+    libc.include.llvm-libc-macros.float16_macros
+    libc.src.__support.FPUtil.cast
+    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.macros.config
+  FLAGS
+    ROUND_OPT
+)
+
+add_header_library(
+  truncl
+  HDRS
+    truncl.h
+  DEPENDS
+    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.macros.config
+)
+
+
 add_header_library(
   ufromfp
   HDRS
diff --git a/libc/src/__support/math/round.h b/libc/src/__support/math/round.h
new file mode 100644
index 0000000000000..5bf356974f455
--- /dev/null
+++ b/libc/src/__support/math/round.h
@@ -0,0 +1,29 @@
+//===-- Implementation header for round -------------------------*- 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___SUPPORT_MATH_ROUND_H
+#define LLVM_LIBC_SRC___SUPPORT_MATH_ROUND_H
+
+#include "src/__support/FPUtil/NearestIntegerOperations.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace math {
+
+LIBC_INLINE constexpr double round(double x) {
+#if defined(__LIBC_USE_BUILTIN_ROUND) && !defined(LIBC_HAS_CONSTANT_EVALUATION)
+  return __builtin_round(x);
+#else
+  return fputil::round(x);
+#endif
+}
+
+} // namespace math
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SRC___SUPPORT_MATH_ROUND_H
diff --git a/libc/src/__support/math/roundbf16.h b/libc/src/__support/math/roundbf16.h
new file mode 100644
index 0000000000000..b41a7035db7f2
--- /dev/null
+++ b/libc/src/__support/math/roundbf16.h
@@ -0,0 +1,26 @@
+//===-- Implementation header for roundbf16 ---------------------*- 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___SUPPORT_MATH_ROUNDBF16_H
+#define LLVM_LIBC_SRC___SUPPORT_MATH_ROUNDBF16_H
+
+#include "src/__support/FPUtil/NearestIntegerOperations.h"
+#include "src/__support/FPUtil/bfloat16.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace math {
+
+LIBC_INLINE constexpr bfloat16 roundbf16(bfloat16 x) {
+  return fputil::round(x);
+}
+
+} // namespace math
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SRC___SUPPORT_MATH_ROUNDBF16_H
diff --git a/libc/src/__support/math/roundeven.h b/libc/src/__support/math/roundeven.h
new file mode 100644
index 0000000000000..d26b5384d2dc1
--- /dev/null
+++ b/libc/src/__support/math/roundeven.h
@@ -0,0 +1,30 @@
+//===-- Implementation header for roundeven ---------------------*- 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___SUPPORT_MATH_ROUNDEVEN_H
+#define LLVM_LIBC_SRC___SUPPORT_MATH_ROUNDEVEN_H
+
+#include "src/__support/FPUtil/NearestIntegerOperations.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace math {
+
+LIBC_INLINE constexpr double roundeven(double x) {
+#if defined(__LIBC_USE_BUILTIN_ROUNDEVEN) &&                                   \
+    !defined(LIBC_HAS_CONSTANT_EVALUATION)
+  return __builtin_roundeven(x);
+#else
+  return fputil::round_using_specific_rounding_mode(x, FP_INT_TONEAREST);
+#endif
+}
+
+} // namespace math
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SRC___SUPPORT_MATH_ROUNDEVEN_H
diff --git a/libc/src/__support/math/roundevenbf16.h b/libc/src/__support/math/roundevenbf16.h
new file mode 100644
index 0000000000000..85ea304862081
--- /dev/null
+++ b/libc/src/__support/math/roundevenbf16.h
@@ -0,0 +1,26 @@
+//===-- Implementation header for roundevenbf16 -----------------*- 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___SUPPORT_MATH_ROUNDEVENBF16_H
+#define LLVM_LIBC_SRC___SUPPORT_MATH_ROUNDEVENBF16_H
+
+#include "src/__support/FPUtil/NearestIntegerOperations.h"
+#include "src/__support/FPUtil/bfloat16.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace math {
+
+LIBC_INLINE constexpr bfloat16 roundevenbf16(bfloat16 x) {
+  return fputil::round_using_specific_rounding_mode(x, FP_INT_TONEAREST);
+}
+
+} // namespace math
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SRC___SUPPORT_MATH_ROUNDEVENBF16_H
diff --git a/libc/src/__support/math/roundevenf.h b/libc/src/__support/math/roundevenf.h
new file mode 100644
index 0000000000000..2af77270d0a6c
--- /dev/null
+++ b/libc/src/__support/math/roundevenf.h
@@ -0,0 +1,30 @@
+//===-- Implementation header for roundevenf --------------------*- 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___SUPPORT_MATH_ROUNDEVENF_H
+#define LLVM_LIBC_SRC___SUPPORT_MATH_ROUNDEVENF_H
+
+#include "src/__support/FPUtil/NearestIntegerOperations.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace math {
+
+LIBC_INLINE constexpr float roundevenf(float x) {
+#if defined(__LIBC_USE_BUILTIN_ROUNDEVEN) &&                                   \
+    !defined(LIBC_HAS_CONSTANT_EVALUATION)
+  return __builtin_roundevenf(x);
+#else
+  return fputil::round_using_specific_rounding_mode(x, FP_INT_TONEAREST);
+#endif
+}
+
+} // namespace math
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SRC___SUPPORT_MATH_ROUNDEVENF_H
diff --git a/libc/src/__support/math/roundevenf128.h b/libc/src/__support/math/roundevenf128.h
new file mode 100644
index 0000000000000..83524c0e8f1bb
--- /dev/null
+++ b/libc/src/__support/math/roundevenf128.h
@@ -0,0 +1,31 @@
+//===-- Implementation header for roundevenf128 -----------------*- 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___SUPPORT_MATH_ROUNDEVENF128_H
+#define LLVM_LIBC_SRC___SUPPORT_MATH_ROUNDEVENF128_H
+
+#include "include/llvm-libc-types/float128.h"
+
+#ifdef LIBC_TYPES_HAS_FLOAT128
+
+#include "src/__support/FPUtil/NearestIntegerOperations.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace math {
+
+LIBC_INLINE constexpr float128 roundevenf128(float128 x) {
+  return fputil::round_using_specific_rounding_mode(x, FP_INT_TONEAREST);
+}
+
+} // namespace math
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LIBC_TYPES_HAS_FLOAT128
+
+#endif // LLVM_LIBC_SRC___SUPPORT_MATH_ROUNDEVENF128_H
diff --git a/libc/src/__support/math/roundevenf16.h b/libc/src/__support/math/roundevenf16.h
new file mode 100644
index 0000000000000..6be3086ff4e9b
--- /dev/null
+++ b/libc/src/__support/math/roundevenf16.h
@@ -0,0 +1,39 @@
+//===-- Implementation header for roundevenf16 ------------------*- 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___SUPPORT_MATH_ROUNDEVENF16_H
+#define LLVM_LIBC_SRC___SUPPORT_MATH_ROUNDEVENF16_H
+
+#include "include/llvm-libc-macros/float16-macros.h"
+
+#ifdef LIBC_TYPES_HAS_FLOAT16
+
+#include "src/__support/FPUtil/NearestIntegerOperations.h"
+#include "src/__support/FPUtil/cast.h"
+#include "src/__support/macros/config.h"
+#include "src/__support/macros/properties/cpu_features.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace math {
+
+LIBC_INLINE constexpr float16 roundevenf16(float16 x) {
+#if defined(__LIBC_USE_BUILTIN_ROUNDEVEN) &&                                   \
+    defined(LIBC_TARGET_CPU_HAS_FAST_FLOAT16_OPS) &&                           \
+    !defined(LIBC_HAS_CONSTANT_EVALUATION)
+  return fputil::cast<float16>(__builtin_roundevenf(x));
+#else
+  return fputil::round_using_specific_rounding_mode(x, FP_INT_TONEAREST);
+#endif
+}
+
+} // namespace math
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LIBC_TYPES_HAS_FLOAT16
+
+#endif // LLVM_LIBC_SRC___SUPPORT_MATH_ROUNDEVENF16_H
diff --git a/libc/src/__support/math/roundevenl.h b/libc/src/__support/math/roundevenl.h
new file mode 100644
index 0000000000000..ed04b7b939230
--- /dev/null
+++ b/libc/src/__support/math/roundevenl.h
@@ -0,0 +1,25 @@
+//===-- Implementation header for roundevenl --------------------*- 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___SUPPORT_MATH_ROUNDEVENL_H
+#define LLVM_LIBC_SRC___SUPPORT_MATH_ROUNDEVENL_H
+
+#include "src/__support/FPUtil/NearestIntegerOperations.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace math {
+
+LIBC_INLINE constexpr long double roundevenl(long double x) {
+  return fputil::round_using_specific_rounding_mode(x, FP_INT_TONEAREST);
+}
+
+} // namespace math
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SRC___SUPPORT_MATH_ROUNDEVENL_H
diff --git a/libc/src/__support/math/roundf.h b/libc/src/__support/math/roundf.h
new file mode 100644
index 0000000000000..94ce6deb6f81a
--- /dev/null
+++ b/libc/src/__support/math/roundf.h
@@ -0,0 +1,29 @@
+//===-- Implementation header for roundf ------------------------*- 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___SUPPORT_MATH_ROUNDF_H
+#define LLVM_LIBC_SRC___SUPPORT_MATH_ROUNDF_H
+
+#include "src/__support/FPUtil/NearestIntegerOperations.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace math {
+
+LIBC_INLINE constexpr float roundf(float x) {
+#if defined(__LIBC_USE_BUILTIN_ROUND) && !defined(LIBC_HAS_CONSTANT_EVALUATION)
+  return __builtin_roundf(x);
+#else
+  return fputil::round(x);
+#endif
+}
+
+} // namespace math
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SRC___SUPPORT_MATH_ROUNDF_H
diff --git a/libc/src/__support/math/roundf128.h b/libc/src/__support/math/roundf128.h
new file mode 100644
index 0000000000000..ccd5a6b10cf53
--- /dev/null
+++ b/libc/src/__support/math/roundf128.h
@@ -0,0 +1,31 @@
+//===-- Implementation header for roundf128 ---------------------*- 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___SUPPORT_MATH_ROUNDF128_H
+#define LLVM_LIBC_SRC___SUPPORT_MATH_ROUNDF128_H
+
+#include "include/llvm-libc-types/float128.h"
+
+#ifdef LIBC_TYPES_HAS_FLOAT128
+
+#include "src/__support/FPUtil/NearestIntegerOperations.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace math {
+
+LIBC_INLINE constexpr float128 roundf128(float128 x) {
+  return fputil::round(x);
+}
+
+} // namespace math
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LIBC_TYPES_HAS_FLOAT128
+
+#endif // LLVM_LIBC_SRC___SUPPORT_MATH_ROUNDF128_H
diff --git a/libc/src/__support/math/roundf16.h b/libc/src/__support/math/roundf16.h
new file mode 100644
index 0000000000000..e525d80d6be53
--- /dev/null
+++ b/libc/src/__support/math/roundf16.h
@@ -0,0 +1,39 @@
+//===-- Implementation header for roundf16 ----------------------*- 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___SUPPORT_MATH_ROUNDF16_H
+#define LLVM_LIBC_SRC___SUPPORT_MATH_ROUNDF16_H
+
+#include "include/llvm-libc-macros/float16-macros.h"
+
+#ifdef LIBC_TYPES_HAS_FLOAT16
+
+#include "src/__support/FPUtil/NearestIntegerOperations.h"
+#include "src/__support/FPUtil/cast.h"
+#include "src/__support/macros/config.h"
+#include "src/__support/macros/properties/cpu_features.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace math {
+
+LIBC_INLINE constexpr float16 roundf16(float16 x) {
+#if defined(__LIBC_USE_BUILTIN_ROUND) &&                                       \
+    defined(LIBC_TARGET_CPU_HAS_FAST_FLOAT16_OPS) &&                           \
+    !defined(LIBC_HAS_CONSTANT_EVALUATION)
+  return fputil::cast<float16>(__builtin_roundf(x));
+#else
+  return fputil::round(x);
+#endif
+}
+
+} // namespace math
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LIBC_TYPES_HAS_FLOAT16
+
+#endif // LLVM_LIBC_SRC___SUPPORT_MATH_ROUNDF16_H
diff --git a/libc/src/__support/math/roundl.h b/libc/src/__support/math/roundl.h
new file mode 100644
index 0000000000000..907157b432589
--- /dev/null
+++ b/libc/src/__support/math/roundl.h
@@ -0,0 +1,25 @@
+//===-- Implementation header for roundl ------------------------*- 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___SUPPORT_MATH_ROUNDL_H
+#define LLVM_LIBC_SRC___SUPPORT_MATH_ROUNDL_H
+
+#include "src/__support/FPUtil/NearestIntegerOperations.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace math {
+
+LIBC_INLINE constexpr long double roundl(long double x) {
+  return fputil::round(x);
+}
+
+} // namespace math
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SRC___SUPPORT_MATH_ROUNDL_H
diff --git a/libc/src/__support/math/trunc.h b/libc/src/__support/math/trunc.h
new file mode 100644
index 0000000000000..2a8c6c739a9af
--- /dev/null
+++ b/libc/src/__support/math/trunc.h
@@ -0,0 +1,30 @@
+//===-- Implementation header for trunc -------------------------*- 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___SUPPORT_MATH_TRUNC_H
+#define LLVM_LIBC_SRC___SUPPORT_MATH_TRUNC_H
+
+#include "src/__support/FPUtil/NearestIntegerOperations.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace math {
+
+LIBC_INLINE constexpr double trunc(double x) {
+#if defined(__LIBC_USE_BUILTIN_CEIL_FLOOR_RINT_TRUNC) &&                       \
+    !defined(LIBC_HAS_CONSTANT_EVALUATION)
+  return __builtin_trunc(x);
+#else
+  return fputil::trunc(x);
+#endif
+}
+
+} // namespace math
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SRC___SUPPORT_MATH_TRUNC_H
diff --git a/libc/src/__support/math/truncbf16.h b/libc/src/__support/math/truncbf16.h
new file mode 100644
index 0000000000000..30635be2d9463
--- /dev/null
+++ b/libc/src/__support/math/truncbf16.h
@@ -0,0 +1,26 @@
+//===-- Implementation header for truncbf16 ---------------------*- 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___SUPPORT_MATH_TRUNCBF16_H
+#define LLVM_LIBC_SRC___SUPPORT_MATH_TRUNCBF16_H
+
+#include "src/__support/FPUtil/NearestIntegerOperations.h"
+#include "src/__support/FPUtil/bfloat16.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace math {
+
+LIBC_INLINE constexpr bfloat16 truncbf16(bfloat16 x) {
+  return fputil::trunc(x);
+}
+
+} // namespace math
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SRC___SUPPORT_MATH_TRUNCBF16_H
diff --git a/libc/src/__support/math/truncf.h b/libc/src/__support/math/truncf.h
new file mode 100644
index 0000000000000..bf6b529b68de9
--- /dev/null
+++ b/libc/src/__support/math/truncf.h
@@ -0,0 +1,30 @@
+//===-- Implementation header for truncf ------------------------*- 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___SUPPORT_MATH_TRUNCF_H
+#define LLVM_LIBC_SRC___SUPPORT_MATH_TRUNCF_H
+
+#include "src/__support/FPUtil/NearestIntegerOperations.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace math {
+
+LIBC_INLINE constexpr float truncf(float x) {
+#if defined(__LIBC_USE_BUILTIN_CEIL_FLOOR_RINT_TRUNC) &&                       \
+    !defined(LIBC_HAS_CONSTANT_EVALUATION)
+  return __builtin_truncf(x);
+#else
+  return fputil::trunc(x);
+#endif
+}
+
+} // namespace math
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SRC___SUPPORT_MATH_TRUNCF_H
diff --git a/libc/src/__support/math/truncf128.h b/libc/src/__support/math/truncf128.h
new file mode 100644
index 0000000000000..e10c3bf667299
--- /dev/null
+++ b/libc/src/__support/math/truncf128.h
@@ -0,0 +1,31 @@
+//===-- Implementation header for truncf128 ---------------------*- 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___SUPPORT_MATH_TRUNCF128_H
+#define LLVM_LIBC_SRC___SUPPORT_MATH_TRUNCF128_H
+
+#include "include/llvm-libc-types/float128.h"
+
+#ifdef LIBC_TYPES_HAS_FLOAT128
+
+#include "src/__support/FPUtil/NearestIntegerOperations.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace math {
+
+LIBC_INLINE constexpr float128 truncf128(float128 x) {
+  return fputil::trunc(x);
+}
+
+} // namespace math
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LIBC_TYPES_HAS_FLOAT128
+
+#endif // LLVM_LIBC_SRC___SUPPORT_MATH_TRUNCF128_H
diff --git a/libc/src/__support/math/truncf16.h b/libc/src/__support/math/truncf16.h
new file mode 100644
index 0000000000000..5e2721a8318ad
--- /dev/null
+++ b/libc/src/__support/math/truncf16.h
@@ -0,0 +1,39 @@
+//===-- Implementation header for truncf16 ----------------------*- 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___SUPPORT_MATH_TRUNCF16_H
+#define LLVM_LIBC_SRC___SUPPORT_MATH_TRUNCF16_H
+
+#include "include/llvm-libc-macros/float16-macros.h"
+
+#ifdef LIBC_TYPES_HAS_FLOAT16
+
+#include "src/__support/FPUtil/NearestIntegerOperations.h"
+#include "src/__support/FPUtil/cast.h"
+#include "src/__support/macros/config.h"
+#include "src/__support/macros/properties/cpu_features.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace math {
+
+LIBC_INLINE constexpr float16 truncf16(float16 x) {
+#if defined(__LIBC_USE_BUILTIN_CEIL_FLOOR_RINT_TRUNC) &&                       \
+    defined(LIBC_TARGET_CPU_HAS_FAST_FLOAT16_OPS) &&                           \
+    !defined(LIBC_HAS_CONSTANT_EVALUATION)
+  return fputil::cast<float16>(__builtin_truncf(x));
+#else
+  return fputil::trunc(x);
+#endif
+}
+
+} // namespace math
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LIBC_TYPES_HAS_FLOAT16
+
+#endif // LLVM_LIBC_SRC___SUPPORT_MATH_TRUNCF16_H
diff --git a/libc/src/__support/math/truncl.h b/libc/src/__support/math/truncl.h
new file mode 100644
index 0000000000000..b546eb18480fa
--- /dev/null
+++ b/libc/src/__support/math/truncl.h
@@ -0,0 +1,25 @@
+//===-- Implementation header for truncl ------------------------*- 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___SUPPORT_MATH_TRUNCL_H
+#define LLVM_LIBC_SRC___SUPPORT_MATH_TRUNCL_H
+
+#include "src/__support/FPUtil/NearestIntegerOperations.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace math {
+
+LIBC_INLINE constexpr long double truncl(long double x) {
+  return fputil::trunc(x);
+}
+
+} // namespace math
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SRC___SUPPORT_MATH_TRUNCL_H
diff --git a/libc/src/math/generic/CMakeLists.txt b/libc/src/math/generic/CMakeLists.txt
index e4ec5838eda4e..5ccd2b3af1c2b 100644
--- a/libc/src/math/generic/CMakeLists.txt
+++ b/libc/src/math/generic/CMakeLists.txt
@@ -553,9 +553,7 @@ add_entrypoint_object(
   HDRS
     ../trunc.h
   DEPENDS
-    libc.src.__support.FPUtil.nearest_integer_operations
-  FLAGS
-    ROUND_OPT
+    libc.src.__support.math.trunc
 )
 
 add_entrypoint_object(
@@ -565,9 +563,7 @@ add_entrypoint_object(
   HDRS
     ../truncf.h
   DEPENDS
-    libc.src.__support.FPUtil.nearest_integer_operations
-  FLAGS
-    ROUND_OPT
+    libc.src.__support.math.truncf
 )
 
 add_entrypoint_object(
@@ -577,7 +573,7 @@ add_entrypoint_object(
   HDRS
     ../truncl.h
   DEPENDS
-    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.math.truncl
 )
 
 add_entrypoint_object(
@@ -587,12 +583,7 @@ add_entrypoint_object(
   HDRS
     ../truncf16.h
   DEPENDS
-    libc.src.__support.FPUtil.cast
-    libc.src.__support.FPUtil.nearest_integer_operations
-    libc.src.__support.macros.properties.cpu_features
-    libc.src.__support.macros.properties.types
-  FLAGS
-    ROUND_OPT
+    libc.src.__support.math.truncf16
 )
 
 add_entrypoint_object(
@@ -602,8 +593,7 @@ add_entrypoint_object(
   HDRS
     ../truncf128.h
   DEPENDS
-    libc.src.__support.macros.properties.types
-    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.math.truncf128
 )
 
 add_entrypoint_object(
@@ -613,13 +603,7 @@ add_entrypoint_object(
   HDRS
     ../truncbf16.h
   DEPENDS
-    libc.src.__support.common
-    libc.src.__support.FPUtil.bfloat16
-    libc.src.__support.FPUtil.nearest_integer_operations
-    libc.src.__support.macros.config
-    libc.src.__support.macros.properties.types
-  FLAGS
-    ROUND_OPT
+    libc.src.__support.math.truncbf16
 )
 
 add_entrypoint_object(
@@ -689,9 +673,7 @@ add_entrypoint_object(
   HDRS
     ../round.h
   DEPENDS
-    libc.src.__support.FPUtil.nearest_integer_operations
-  FLAGS
-    ROUND_OPT
+    libc.src.__support.math.round
 )
 
 add_entrypoint_object(
@@ -701,9 +683,7 @@ add_entrypoint_object(
   HDRS
     ../roundf.h
   DEPENDS
-    libc.src.__support.FPUtil.nearest_integer_operations
-  FLAGS
-    ROUND_OPT
+    libc.src.__support.math.roundf
 )
 
 add_entrypoint_object(
@@ -713,7 +693,7 @@ add_entrypoint_object(
   HDRS
     ../roundl.h
   DEPENDS
-    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.math.roundl
 )
 
 add_entrypoint_object(
@@ -723,12 +703,7 @@ add_entrypoint_object(
   HDRS
     ../roundf16.h
   DEPENDS
-    libc.src.__support.FPUtil.cast
-    libc.src.__support.FPUtil.nearest_integer_operations
-    libc.src.__support.macros.properties.cpu_features
-    libc.src.__support.macros.properties.types
-  FLAGS
-    ROUND_OPT
+    libc.src.__support.math.roundf16
 )
 
 add_entrypoint_object(
@@ -738,8 +713,7 @@ add_entrypoint_object(
   HDRS
     ../roundf128.h
   DEPENDS
-    libc.src.__support.macros.properties.types
-    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.math.roundf128
 )
 
 add_entrypoint_object(
@@ -749,13 +723,7 @@ add_entrypoint_object(
   HDRS
     ../roundbf16.h
   DEPENDS
-    libc.src.__support.common
-    libc.src.__support.FPUtil.bfloat16
-    libc.src.__support.FPUtil.nearest_integer_operations
-    libc.src.__support.macros.config
-    libc.src.__support.macros.properties.types
-  FLAGS
-    ROUND_OPT
+    libc.src.__support.math.roundbf16
 )
 
 add_entrypoint_object(
@@ -765,9 +733,7 @@ add_entrypoint_object(
   HDRS
     ../roundeven.h
   DEPENDS
-    libc.src.__support.FPUtil.nearest_integer_operations
-  FLAGS
-    ROUND_OPT
+    libc.src.__support.math.roundeven
 )
 
 add_entrypoint_object(
@@ -777,9 +743,7 @@ add_entrypoint_object(
   HDRS
     ../roundevenf.h
   DEPENDS
-    libc.src.__support.FPUtil.nearest_integer_operations
-  FLAGS
-    ROUND_OPT
+    libc.src.__support.math.roundevenf
 )
 
 add_entrypoint_object(
@@ -789,7 +753,7 @@ add_entrypoint_object(
   HDRS
     ../roundevenl.h
   DEPENDS
-    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.math.roundevenl
 )
 
 add_entrypoint_object(
@@ -799,12 +763,7 @@ add_entrypoint_object(
   HDRS
     ../roundevenf16.h
   DEPENDS
-    libc.src.__support.macros.properties.types
-    libc.src.__support.FPUtil.nearest_integer_operations
-    libc.src.__support.FPUtil.cast
-    libc.src.__support.macros.properties.cpu_features
-  FLAGS
-    ROUND_OPT
+    libc.src.__support.math.roundevenf16
 )
 
 add_entrypoint_object(
@@ -814,8 +773,7 @@ add_entrypoint_object(
   HDRS
     ../roundevenf128.h
   DEPENDS
-    libc.src.__support.macros.properties.types
-    libc.src.__support.FPUtil.nearest_integer_operations
+    libc.src.__support.math.roundevenf128
 )
 
 add_entrypoint_object(
@@ -825,13 +783,7 @@ add_entrypoint_object(
   HDRS
     ../roundevenbf16.h
   DEPENDS
-    libc.src.__support.common
-    libc.src.__support.FPUtil.bfloat16
-    libc.src.__support.FPUtil.nearest_integer_operations
-    libc.src.__support.macros.config
-    libc.src.__support.macros.properties.types
-  FLAGS
-    ROUND_OPT
+    libc.src.__support.math.roundevenbf16
 )
 
 add_entrypoint_object(
diff --git a/libc/src/math/generic/round.cpp b/libc/src/math/generic/round.cpp
index 6ed5be5065962..3a9d0e2c18f2d 100644
--- a/libc/src/math/generic/round.cpp
+++ b/libc/src/math/generic/round.cpp
@@ -7,18 +7,10 @@
 //===----------------------------------------------------------------------===//
 
 #include "src/math/round.h"
-#include "src/__support/FPUtil/NearestIntegerOperations.h"
-#include "src/__support/common.h"
-#include "src/__support/macros/config.h"
+#include "src/__support/math/round.h"
 
 namespace LIBC_NAMESPACE_DECL {
 
-LLVM_LIBC_FUNCTION(double, round, (double x)) {
-#ifdef __LIBC_USE_BUILTIN_ROUND
-  return __builtin_round(x);
-#else
-  return fputil::round(x);
-#endif
-}
+LLVM_LIBC_FUNCTION(double, round, (double x)) { return math::round(x); }
 
 } // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/math/generic/roundbf16.cpp b/libc/src/math/generic/roundbf16.cpp
index cc7e5e2375d58..894a69681de2d 100644
--- a/libc/src/math/generic/roundbf16.cpp
+++ b/libc/src/math/generic/roundbf16.cpp
@@ -7,15 +7,12 @@
 //===----------------------------------------------------------------------===//
 
 #include "src/math/roundbf16.h"
-#include "src/__support/FPUtil/NearestIntegerOperations.h"
-#include "src/__support/FPUtil/bfloat16.h"
-#include "src/__support/common.h"
-#include "src/__support/macros/config.h"
+#include "src/__support/math/roundbf16.h"
 
 namespace LIBC_NAMESPACE_DECL {
 
 LLVM_LIBC_FUNCTION(bfloat16, roundbf16, (bfloat16 x)) {
-  return fputil::round(x);
+  return math::roundbf16(x);
 }
 
 } // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/math/generic/roundeven.cpp b/libc/src/math/generic/roundeven.cpp
index 42f19f38b5385..dda76173438ac 100644
--- a/libc/src/math/generic/roundeven.cpp
+++ b/libc/src/math/generic/roundeven.cpp
@@ -7,18 +7,10 @@
 //===----------------------------------------------------------------------===//
 
 #include "src/math/roundeven.h"
-#include "src/__support/FPUtil/NearestIntegerOperations.h"
-#include "src/__support/common.h"
-#include "src/__support/macros/config.h"
+#include "src/__support/math/roundeven.h"
 
 namespace LIBC_NAMESPACE_DECL {
 
-LLVM_LIBC_FUNCTION(double, roundeven, (double x)) {
-#ifdef __LIBC_USE_BUILTIN_ROUNDEVEN
-  return __builtin_roundeven(x);
-#else
-  return fputil::round_using_specific_rounding_mode(x, FP_INT_TONEAREST);
-#endif
-}
+LLVM_LIBC_FUNCTION(double, roundeven, (double x)) { return math::roundeven(x); }
 
 } // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/math/generic/roundevenbf16.cpp b/libc/src/math/generic/roundevenbf16.cpp
index 39419e483fb9e..0986d6f99b7df 100644
--- a/libc/src/math/generic/roundevenbf16.cpp
+++ b/libc/src/math/generic/roundevenbf16.cpp
@@ -7,15 +7,12 @@
 //===----------------------------------------------------------------------===//
 
 #include "src/math/roundevenbf16.h"
-#include "src/__support/FPUtil/NearestIntegerOperations.h"
-#include "src/__support/FPUtil/bfloat16.h"
-#include "src/__support/common.h"
-#include "src/__support/macros/config.h"
+#include "src/__support/math/roundevenbf16.h"
 
 namespace LIBC_NAMESPACE_DECL {
 
 LLVM_LIBC_FUNCTION(bfloat16, roundevenbf16, (bfloat16 x)) {
-  return fputil::round_using_specific_rounding_mode(x, FP_INT_TONEAREST);
+  return math::roundevenbf16(x);
 }
 
 } // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/math/generic/roundevenf.cpp b/libc/src/math/generic/roundevenf.cpp
index 98bdc6545d94e..8536397f110a8 100644
--- a/libc/src/math/generic/roundevenf.cpp
+++ b/libc/src/math/generic/roundevenf.cpp
@@ -7,18 +7,10 @@
 //===----------------------------------------------------------------------===//
 
 #include "src/math/roundevenf.h"
-#include "src/__support/FPUtil/NearestIntegerOperations.h"
-#include "src/__support/common.h"
-#include "src/__support/macros/config.h"
+#include "src/__support/math/roundevenf.h"
 
 namespace LIBC_NAMESPACE_DECL {
 
-LLVM_LIBC_FUNCTION(float, roundevenf, (float x)) {
-#ifdef __LIBC_USE_BUILTIN_ROUNDEVEN
-  return __builtin_roundevenf(x);
-#else
-  return fputil::round_using_specific_rounding_mode(x, FP_INT_TONEAREST);
-#endif
-}
+LLVM_LIBC_FUNCTION(float, roundevenf, (float x)) { return math::roundevenf(x); }
 
 } // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/math/generic/roundevenf128.cpp b/libc/src/math/generic/roundevenf128.cpp
index 354076b4a68f8..6b36c53d50756 100644
--- a/libc/src/math/generic/roundevenf128.cpp
+++ b/libc/src/math/generic/roundevenf128.cpp
@@ -7,14 +7,12 @@
 //===----------------------------------------------------------------------===//
 
 #include "src/math/roundevenf128.h"
-#include "src/__support/FPUtil/NearestIntegerOperations.h"
-#include "src/__support/common.h"
-#include "src/__support/macros/config.h"
+#include "src/__support/math/roundevenf128.h"
 
 namespace LIBC_NAMESPACE_DECL {
 
 LLVM_LIBC_FUNCTION(float128, roundevenf128, (float128 x)) {
-  return fputil::round_using_specific_rounding_mode(x, FP_INT_TONEAREST);
+  return math::roundevenf128(x);
 }
 
 } // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/math/generic/roundevenf16.cpp b/libc/src/math/generic/roundevenf16.cpp
index fdcd968bc9b87..e01a61e6fafbe 100644
--- a/libc/src/math/generic/roundevenf16.cpp
+++ b/libc/src/math/generic/roundevenf16.cpp
@@ -7,21 +7,12 @@
 //===----------------------------------------------------------------------===//
 
 #include "src/math/roundevenf16.h"
-#include "src/__support/FPUtil/NearestIntegerOperations.h"
-#include "src/__support/FPUtil/cast.h"
-#include "src/__support/common.h"
-#include "src/__support/macros/config.h"
-#include "src/__support/macros/properties/cpu_features.h"
+#include "src/__support/math/roundevenf16.h"
 
 namespace LIBC_NAMESPACE_DECL {
 
 LLVM_LIBC_FUNCTION(float16, roundevenf16, (float16 x)) {
-#if defined(__LIBC_USE_BUILTIN_ROUNDEVEN) &&                                   \
-    defined(LIBC_TARGET_CPU_HAS_FAST_FLOAT16_OPS)
-  return fputil::cast<float16>(__builtin_roundevenf(x));
-#else
-  return fputil::round_using_specific_rounding_mode(x, FP_INT_TONEAREST);
-#endif
+  return math::roundevenf16(x);
 }
 
 } // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/math/generic/roundevenl.cpp b/libc/src/math/generic/roundevenl.cpp
index 6ffe80a0f1d12..996510510f460 100644
--- a/libc/src/math/generic/roundevenl.cpp
+++ b/libc/src/math/generic/roundevenl.cpp
@@ -7,14 +7,12 @@
 //===----------------------------------------------------------------------===//
 
 #include "src/math/roundevenl.h"
-#include "src/__support/FPUtil/NearestIntegerOperations.h"
-#include "src/__support/common.h"
-#include "src/__support/macros/config.h"
+#include "src/__support/math/roundevenl.h"
 
 namespace LIBC_NAMESPACE_DECL {
 
 LLVM_LIBC_FUNCTION(long double, roundevenl, (long double x)) {
-  return fputil::round_using_specific_rounding_mode(x, FP_INT_TONEAREST);
+  return math::roundevenl(x);
 }
 
 } // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/math/generic/roundf.cpp b/libc/src/math/generic/roundf.cpp
index d25f7128cb9ce..589a1e9a8f217 100644
--- a/libc/src/math/generic/roundf.cpp
+++ b/libc/src/math/generic/roundf.cpp
@@ -7,18 +7,10 @@
 //===----------------------------------------------------------------------===//
 
 #include "src/math/roundf.h"
-#include "src/__support/FPUtil/NearestIntegerOperations.h"
-#include "src/__support/common.h"
-#include "src/__support/macros/config.h"
+#include "src/__support/math/roundf.h"
 
 namespace LIBC_NAMESPACE_DECL {
 
-LLVM_LIBC_FUNCTION(float, roundf, (float x)) {
-#ifdef __LIBC_USE_BUILTIN_ROUND
-  return __builtin_roundf(x);
-#else
-  return fputil::round(x);
-#endif
-}
+LLVM_LIBC_FUNCTION(float, roundf, (float x)) { return math::roundf(x); }
 
 } // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/math/generic/roundf128.cpp b/libc/src/math/generic/roundf128.cpp
index 88a545e78dcdb..5b2b4c44b2f98 100644
--- a/libc/src/math/generic/roundf128.cpp
+++ b/libc/src/math/generic/roundf128.cpp
@@ -7,14 +7,12 @@
 //===----------------------------------------------------------------------===//
 
 #include "src/math/roundf128.h"
-#include "src/__support/FPUtil/NearestIntegerOperations.h"
-#include "src/__support/common.h"
-#include "src/__support/macros/config.h"
+#include "src/__support/math/roundf128.h"
 
 namespace LIBC_NAMESPACE_DECL {
 
 LLVM_LIBC_FUNCTION(float128, roundf128, (float128 x)) {
-  return fputil::round(x);
+  return math::roundf128(x);
 }
 
 } // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/math/generic/roundf16.cpp b/libc/src/math/generic/roundf16.cpp
index 9adfb52ed27c6..064ad877b2f6e 100644
--- a/libc/src/math/generic/roundf16.cpp
+++ b/libc/src/math/generic/roundf16.cpp
@@ -7,21 +7,10 @@
 //===----------------------------------------------------------------------===//
 
 #include "src/math/roundf16.h"
-#include "src/__support/FPUtil/NearestIntegerOperations.h"
-#include "src/__support/FPUtil/cast.h"
-#include "src/__support/common.h"
-#include "src/__support/macros/config.h"
-#include "src/__support/macros/properties/cpu_features.h"
+#include "src/__support/math/roundf16.h"
 
 namespace LIBC_NAMESPACE_DECL {
 
-LLVM_LIBC_FUNCTION(float16, roundf16, (float16 x)) {
-#if defined(__LIBC_USE_BUILTIN_ROUND) &&                                       \
-    defined(LIBC_TARGET_CPU_HAS_FAST_FLOAT16_OPS)
-  return fputil::cast<float16>(__builtin_roundf(x));
-#else
-  return fputil::round(x);
-#endif
-}
+LLVM_LIBC_FUNCTION(float16, roundf16, (float16 x)) { return math::roundf16(x); }
 
 } // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/math/generic/roundl.cpp b/libc/src/math/generic/roundl.cpp
index 0f7b29e1907cf..a6774efa9b84e 100644
--- a/libc/src/math/generic/roundl.cpp
+++ b/libc/src/math/generic/roundl.cpp
@@ -7,14 +7,12 @@
 //===----------------------------------------------------------------------===//
 
 #include "src/math/roundl.h"
-#include "src/__support/FPUtil/NearestIntegerOperations.h"
-#include "src/__support/common.h"
-#include "src/__support/macros/config.h"
+#include "src/__support/math/roundl.h"
 
 namespace LIBC_NAMESPACE_DECL {
 
 LLVM_LIBC_FUNCTION(long double, roundl, (long double x)) {
-  return fputil::round(x);
+  return math::roundl(x);
 }
 
 } // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/math/generic/trunc.cpp b/libc/src/math/generic/trunc.cpp
index 603750f11c9f6..1ef88f4a1552c 100644
--- a/libc/src/math/generic/trunc.cpp
+++ b/libc/src/math/generic/trunc.cpp
@@ -7,18 +7,10 @@
 //===----------------------------------------------------------------------===//
 
 #include "src/math/trunc.h"
-#include "src/__support/FPUtil/NearestIntegerOperations.h"
-#include "src/__support/common.h"
-#include "src/__support/macros/config.h"
+#include "src/__support/math/trunc.h"
 
 namespace LIBC_NAMESPACE_DECL {
 
-LLVM_LIBC_FUNCTION(double, trunc, (double x)) {
-#ifdef __LIBC_USE_BUILTIN_CEIL_FLOOR_RINT_TRUNC
-  return __builtin_trunc(x);
-#else
-  return fputil::trunc(x);
-#endif
-}
+LLVM_LIBC_FUNCTION(double, trunc, (double x)) { return math::trunc(x); }
 
 } // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/math/generic/truncbf16.cpp b/libc/src/math/generic/truncbf16.cpp
index dfbe83d003377..49ec61ffde4ba 100644
--- a/libc/src/math/generic/truncbf16.cpp
+++ b/libc/src/math/generic/truncbf16.cpp
@@ -7,15 +7,12 @@
 //===----------------------------------------------------------------------===//
 
 #include "src/math/truncbf16.h"
-#include "src/__support/FPUtil/NearestIntegerOperations.h"
-#include "src/__support/FPUtil/bfloat16.h"
-#include "src/__support/common.h"
-#include "src/__support/macros/config.h"
+#include "src/__support/math/truncbf16.h"
 
 namespace LIBC_NAMESPACE_DECL {
 
 LLVM_LIBC_FUNCTION(bfloat16, truncbf16, (bfloat16 x)) {
-  return fputil::trunc(x);
+  return math::truncbf16(x);
 }
 
 } // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/math/generic/truncf.cpp b/libc/src/math/generic/truncf.cpp
index d7b0ffd96da9c..20a0fcd8dc140 100644
--- a/libc/src/math/generic/truncf.cpp
+++ b/libc/src/math/generic/truncf.cpp
@@ -7,18 +7,10 @@
 //===----------------------------------------------------------------------===//
 
 #include "src/math/truncf.h"
-#include "src/__support/FPUtil/NearestIntegerOperations.h"
-#include "src/__support/common.h"
-#include "src/__support/macros/config.h"
+#include "src/__support/math/truncf.h"
 
 namespace LIBC_NAMESPACE_DECL {
 
-LLVM_LIBC_FUNCTION(float, truncf, (float x)) {
-#ifdef __LIBC_USE_BUILTIN_CEIL_FLOOR_RINT_TRUNC
-  return __builtin_truncf(x);
-#else
-  return fputil::trunc(x);
-#endif
-}
+LLVM_LIBC_FUNCTION(float, truncf, (float x)) { return math::truncf(x); }
 
 } // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/math/generic/truncf128.cpp b/libc/src/math/generic/truncf128.cpp
index 200dbf1286af9..bef079cbbd6a5 100644
--- a/libc/src/math/generic/truncf128.cpp
+++ b/libc/src/math/generic/truncf128.cpp
@@ -7,14 +7,12 @@
 //===----------------------------------------------------------------------===//
 
 #include "src/math/truncf128.h"
-#include "src/__support/FPUtil/NearestIntegerOperations.h"
-#include "src/__support/common.h"
-#include "src/__support/macros/config.h"
+#include "src/__support/math/truncf128.h"
 
 namespace LIBC_NAMESPACE_DECL {
 
 LLVM_LIBC_FUNCTION(float128, truncf128, (float128 x)) {
-  return fputil::trunc(x);
+  return math::truncf128(x);
 }
 
 } // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/math/generic/truncf16.cpp b/libc/src/math/generic/truncf16.cpp
index 4d37e6560a965..2925e31fc2a52 100644
--- a/libc/src/math/generic/truncf16.cpp
+++ b/libc/src/math/generic/truncf16.cpp
@@ -7,21 +7,10 @@
 //===----------------------------------------------------------------------===//
 
 #include "src/math/truncf16.h"
-#include "src/__support/FPUtil/NearestIntegerOperations.h"
-#include "src/__support/FPUtil/cast.h"
-#include "src/__support/common.h"
-#include "src/__support/macros/config.h"
-#include "src/__support/macros/properties/cpu_features.h"
+#include "src/__support/math/truncf16.h"
 
 namespace LIBC_NAMESPACE_DECL {
 
-LLVM_LIBC_FUNCTION(float16, truncf16, (float16 x)) {
-#if defined(__LIBC_USE_BUILTIN_CEIL_FLOOR_RINT_TRUNC) &&                       \
-    defined(LIBC_TARGET_CPU_HAS_FAST_FLOAT16_OPS)
-  return fputil::cast<float16>(__builtin_truncf(x));
-#else
-  return fputil::trunc(x);
-#endif
-}
+LLVM_LIBC_FUNCTION(float16, truncf16, (float16 x)) { return math::truncf16(x); }
 
 } // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/src/math/generic/truncl.cpp b/libc/src/math/generic/truncl.cpp
index 83b0827d4a192..2d9265da29487 100644
--- a/libc/src/math/generic/truncl.cpp
+++ b/libc/src/math/generic/truncl.cpp
@@ -7,14 +7,12 @@
 //===----------------------------------------------------------------------===//
 
 #include "src/math/truncl.h"
-#include "src/__support/FPUtil/NearestIntegerOperations.h"
-#include "src/__support/common.h"
-#include "src/__support/macros/config.h"
+#include "src/__support/math/truncl.h"
 
 namespace LIBC_NAMESPACE_DECL {
 
 LLVM_LIBC_FUNCTION(long double, truncl, (long double x)) {
-  return fputil::trunc(x);
+  return math::truncl(x);
 }
 
 } // namespace LIBC_NAMESPACE_DECL
diff --git a/libc/test/shared/CMakeLists.txt b/libc/test/shared/CMakeLists.txt
index 680491878705c..23a40e390d70b 100644
--- a/libc/test/shared/CMakeLists.txt
+++ b/libc/test/shared/CMakeLists.txt
@@ -408,6 +408,18 @@ add_fp_unittest(
     libc.src.__support.math.rintf128
     libc.src.__support.math.rintf16
     libc.src.__support.math.rintl
+    libc.src.__support.math.round
+    libc.src.__support.math.roundbf16
+    libc.src.__support.math.roundeven
+    libc.src.__support.math.roundevenbf16
+    libc.src.__support.math.roundevenf
+    libc.src.__support.math.roundevenf128
+    libc.src.__support.math.roundevenf16
+    libc.src.__support.math.roundevenl
+    libc.src.__support.math.roundf
+    libc.src.__support.math.roundf128
+    libc.src.__support.math.roundf16
+    libc.src.__support.math.roundl
     libc.src.__support.math.rsqrtf
     libc.src.__support.math.rsqrtf16
     libc.src.__support.math.scalbln
@@ -456,6 +468,12 @@ add_fp_unittest(
     libc.src.__support.math.tanhf16
     libc.src.__support.math.tanpif
     libc.src.__support.math.tanpif16
+    libc.src.__support.math.trunc
+    libc.src.__support.math.truncbf16
+    libc.src.__support.math.truncf
+    libc.src.__support.math.truncf128
+    libc.src.__support.math.truncf16
+    libc.src.__support.math.truncl
     libc.src.__support.math.ufromfp
     libc.src.__support.math.ufromfpbf16
     libc.src.__support.math.ufromfpf
@@ -702,6 +720,18 @@ add_fp_unittest(
     libc.src.__support.math.rintf128
     libc.src.__support.math.rintf16
     libc.src.__support.math.rintl
+    libc.src.__support.math.round
+    libc.src.__support.math.roundbf16
+    libc.src.__support.math.roundeven
+    libc.src.__support.math.roundevenbf16
+    libc.src.__support.math.roundevenf
+    libc.src.__support.math.roundevenf128
+    libc.src.__support.math.roundevenf16
+    libc.src.__support.math.roundevenl
+    libc.src.__support.math.roundf
+    libc.src.__support.math.roundf128
+    libc.src.__support.math.roundf16
+    libc.src.__support.math.roundl
     libc.src.__support.math.scalbln
     libc.src.__support.math.scalblnbf16
     libc.src.__support.math.scalblnf
@@ -721,6 +751,12 @@ add_fp_unittest(
     libc.src.__support.math.setpayloadf16
     libc.src.__support.math.setpayloadl
     libc.src.__support.math.sqrtl
+    libc.src.__support.math.trunc
+    libc.src.__support.math.truncbf16
+    libc.src.__support.math.truncf
+    libc.src.__support.math.truncf128
+    libc.src.__support.math.truncf16
+    libc.src.__support.math.truncl
     libc.src.__support.math.ufromfp
     libc.src.__support.math.ufromfpbf16
     libc.src.__support.math.ufromfpf
diff --git a/libc/test/shared/shared_math_constexpr_test.cpp b/libc/test/shared/shared_math_constexpr_test.cpp
index e99f8691451a3..9cacb20439ae5 100644
--- a/libc/test/shared/shared_math_constexpr_test.cpp
+++ b/libc/test/shared/shared_math_constexpr_test.cpp
@@ -84,6 +84,9 @@ static_assert(1 == [] {
              LIBC_NAMESPACE::shared::nan(&arg))
       .is_nan();
 }());
+static_assert(0.0 == LIBC_NAMESPACE::shared::round(0.0));
+static_assert(0.0 == LIBC_NAMESPACE::shared::roundeven(0.0));
+static_assert(0.0 == LIBC_NAMESPACE::shared::trunc(0.0));
 
 //===----------------------------------------------------------------------===//
 //                       Float Tests
@@ -154,6 +157,9 @@ static_assert(1 == [] {
              LIBC_NAMESPACE::shared::nanf(&arg))
       .is_nan();
 }());
+static_assert(0.0f == LIBC_NAMESPACE::shared::roundf(0.0f));
+static_assert(0.0f == LIBC_NAMESPACE::shared::roundevenf(0.0f));
+static_assert(0.0f == LIBC_NAMESPACE::shared::truncf(0.0f));
 
 //===----------------------------------------------------------------------===//
 //                       Float16 Tests
@@ -242,6 +248,9 @@ static_assert(1 == [] {
              LIBC_NAMESPACE::shared::nanf16(&arg))
       .is_nan();
 }());
+static_assert(0.0f16 == LIBC_NAMESPACE::shared::roundf16(0.0f16));
+static_assert(0.0f16 == LIBC_NAMESPACE::shared::roundevenf16(0.0f16));
+static_assert(0.0f16 == LIBC_NAMESPACE::shared::truncf16(0.0f16));
 #endif // LIBC_TYPES_HAS_FLOAT16
 
 //===----------------------------------------------------------------------===//
@@ -325,6 +334,9 @@ static_assert(1 == [] {
   const char arg{};
   return LIBC_NAMESPACE::fputil::FPBits<long double>(LIBC_NAMESPACE::shared::nanl(&arg)).is_nan();
 }());
+static_assert(0.0L == LIBC_NAMESPACE::shared::roundl(0.0L));
+static_assert(0.0L == LIBC_NAMESPACE::shared::roundevenl(0.0L));
+static_assert(0.0L == LIBC_NAMESPACE::shared::truncl(0.0L));
 
 #endif
 
@@ -445,6 +457,12 @@ static_assert(1 == [] {
              LIBC_NAMESPACE::shared::nanf128(&arg))
       .is_nan();
 }());
+static_assert(float128(0.0) ==
+              LIBC_NAMESPACE::shared::roundf128(float128(0.0)));
+static_assert(float128(0.0) ==
+              LIBC_NAMESPACE::shared::roundevenf128(float128(0.0)));
+static_assert(float128(0.0) ==
+              LIBC_NAMESPACE::shared::truncf128(float128(0.0)));
 
 #endif // LIBC_TYPES_HAS_FLOAT128
 
@@ -561,5 +579,11 @@ static_assert(bfloat16(1) == [] {
              LIBC_NAMESPACE::shared::nanbf16(&arg))
       .is_nan();
 }());
+static_assert(bfloat16(0.0) ==
+              LIBC_NAMESPACE::shared::roundbf16(bfloat16(0.0)));
+static_assert(bfloat16(0.0) ==
+              LIBC_NAMESPACE::shared::roundevenbf16(bfloat16(0.0)));
+static_assert(bfloat16(0.0) ==
+              LIBC_NAMESPACE::shared::truncbf16(bfloat16(0.0)));
 
 TEST(LlvmLibcSharedMathTest, ConstantEvaluation) {}
diff --git a/libc/test/shared/shared_math_test.cpp b/libc/test/shared/shared_math_test.cpp
index d5753dce2b8ad..a11f5d50c022b 100644
--- a/libc/test/shared/shared_math_test.cpp
+++ b/libc/test/shared/shared_math_test.cpp
@@ -152,6 +152,9 @@ TEST(LlvmLibcSharedMathTest, AllFloat16) {
   EXPECT_EQ(1, LIBC_NAMESPACE::shared::iscanonicalf16(0.0f16));
   EXPECT_EQ(0, LIBC_NAMESPACE::shared::issignalingf16(0.0f16));
   EXPECT_TRUE(FPBits(LIBC_NAMESPACE::shared::nanf16("")).is_nan());
+  EXPECT_FP_EQ(0x0p+0f16, LIBC_NAMESPACE::shared::roundf16(0.0f16));
+  EXPECT_FP_EQ(0x0p+0f16, LIBC_NAMESPACE::shared::roundevenf16(0.0f16));
+  EXPECT_FP_EQ(0x0p+0f16, LIBC_NAMESPACE::shared::truncf16(0.0f16));
 }
 
 #endif // LIBC_TYPES_HAS_FLOAT16
@@ -307,6 +310,9 @@ TEST(LlvmLibcSharedMathTest, AllFloat) {
   EXPECT_EQ(1, LIBC_NAMESPACE::shared::iscanonicalf(0.0f));
   EXPECT_EQ(0, LIBC_NAMESPACE::shared::issignalingf(0.0f));
   EXPECT_TRUE(FPBits(LIBC_NAMESPACE::shared::nanf("")).is_nan());
+  EXPECT_FP_EQ(0x0p+0f, LIBC_NAMESPACE::shared::roundf(0.0f));
+  EXPECT_FP_EQ(0x0p+0f, LIBC_NAMESPACE::shared::roundevenf(0.0f));
+  EXPECT_FP_EQ(0x0p+0f, LIBC_NAMESPACE::shared::truncf(0.0f));
 }
 
 TEST(LlvmLibcSharedMathTest, AllDouble) {
@@ -438,6 +444,9 @@ TEST(LlvmLibcSharedMathTest, AllDouble) {
   EXPECT_EQ(1, LIBC_NAMESPACE::shared::iscanonical(0.0L));
   EXPECT_EQ(0, LIBC_NAMESPACE::shared::issignaling(0.0));
   EXPECT_TRUE(FPBits(LIBC_NAMESPACE::shared::nan("")).is_nan());
+  EXPECT_FP_EQ(0.0, LIBC_NAMESPACE::shared::round(0.0));
+  EXPECT_FP_EQ(0.0, LIBC_NAMESPACE::shared::roundeven(0.0));
+  EXPECT_FP_EQ(0.0, LIBC_NAMESPACE::shared::trunc(0.0));
 }
 
 // TODO: Enable the tests when double-double type is supported.
@@ -551,6 +560,9 @@ TEST(LlvmLibcSharedMathTest, AllLongDouble) {
   EXPECT_EQ(1, LIBC_NAMESPACE::shared::iscanonicall(0.0L));
   EXPECT_EQ(0, LIBC_NAMESPACE::shared::issignalingl(0.0L));
   EXPECT_TRUE(FPBits(LIBC_NAMESPACE::shared::nanl("")).is_nan());
+  EXPECT_FP_EQ(0x0p+0L, LIBC_NAMESPACE::shared::roundl(0.0L));
+  EXPECT_FP_EQ(0x0p+0L, LIBC_NAMESPACE::shared::roundevenl(0.0L));
+  EXPECT_FP_EQ(0x0p+0L, LIBC_NAMESPACE::shared::truncl(0.0L));
 }
 
 #endif // LIBC_TYPES_LONG_DOUBLE_IS_DOUBLE_DOUBLE
@@ -723,6 +735,10 @@ TEST(LlvmLibcSharedMathTest, AllFloat128) {
   EXPECT_EQ(1, LIBC_NAMESPACE::shared::iscanonicalf128(float128(0.0)));
   EXPECT_EQ(0, LIBC_NAMESPACE::shared::issignalingf128(float128(0.0)));
   EXPECT_TRUE(FPBits(LIBC_NAMESPACE::shared::nanf128("")).is_nan());
+  EXPECT_FP_EQ(float128(0.0), LIBC_NAMESPACE::shared::roundf128(float128(0.0)));
+  EXPECT_FP_EQ(float128(0.0),
+               LIBC_NAMESPACE::shared::roundevenf128(float128(0.0)));
+  EXPECT_FP_EQ(float128(0.0), LIBC_NAMESPACE::shared::truncf128(float128(0.0)));
 }
 
 #endif // LIBC_TYPES_HAS_FLOAT128
@@ -858,4 +874,8 @@ TEST(LlvmLibcSharedMathTest, AllBFloat16) {
   EXPECT_EQ(1, LIBC_NAMESPACE::shared::iscanonicalbf16(bfloat16(0.0)));
   EXPECT_EQ(0, LIBC_NAMESPACE::shared::issignalingbf16(bfloat16(0.0)));
   EXPECT_TRUE(FPBits(LIBC_NAMESPACE::shared::nanbf16("")).is_nan());
+  EXPECT_FP_EQ(bfloat16(0.0), LIBC_NAMESPACE::shared::roundbf16(bfloat16(0.0)));
+  EXPECT_FP_EQ(bfloat16(0.0),
+               LIBC_NAMESPACE::shared::roundevenbf16(bfloat16(0.0)));
+  EXPECT_FP_EQ(bfloat16(0.0), LIBC_NAMESPACE::shared::truncbf16(bfloat16(0.0)));
 }
diff --git a/utils/bazel/llvm-project-overlay/libc/BUILD.bazel b/utils/bazel/llvm-project-overlay/libc/BUILD.bazel
index f7de59245489a..cad1fc4e8b3d3 100644
--- a/utils/bazel/llvm-project-overlay/libc/BUILD.bazel
+++ b/utils/bazel/llvm-project-overlay/libc/BUILD.bazel
@@ -5550,6 +5550,122 @@ libc_support_library(
     ],
 )
 
+libc_support_library(
+    name = "__support_math_round",
+    hdrs = ["src/__support/math/round.h"],
+    deps = [
+        ":__support_fputil_nearest_integer_operations",
+        ":__support_macros_config",
+    ],
+)
+
+libc_support_library(
+    name = "__support_math_roundbf16",
+    hdrs = ["src/__support/math/roundbf16.h"],
+    deps = [
+        ":__support_fputil_bfloat16",
+        ":__support_fputil_nearest_integer_operations",
+        ":__support_macros_config",
+    ],
+)
+
+libc_support_library(
+    name = "__support_math_roundeven",
+    hdrs = ["src/__support/math/roundeven.h"],
+    deps = [
+        ":__support_fputil_nearest_integer_operations",
+        ":__support_macros_config",
+    ],
+)
+
+libc_support_library(
+    name = "__support_math_roundevenbf16",
+    hdrs = ["src/__support/math/roundevenbf16.h"],
+    deps = [
+        ":__support_fputil_bfloat16",
+        ":__support_fputil_nearest_integer_operations",
+        ":__support_macros_config",
+    ],
+)
+
+libc_support_library(
+    name = "__support_math_roundevenf",
+    hdrs = ["src/__support/math/roundevenf.h"],
+    deps = [
+        ":__support_fputil_nearest_integer_operations",
+        ":__support_macros_config",
+    ],
+)
+
+libc_support_library(
+    name = "__support_math_roundevenf128",
+    hdrs = ["src/__support/math/roundevenf128.h"],
+    deps = [
+        ":__support_fputil_nearest_integer_operations",
+        ":__support_macros_config",
+        ":llvm_libc_types_float128",
+    ],
+)
+
+libc_support_library(
+    name = "__support_math_roundevenf16",
+    hdrs = ["src/__support/math/roundevenf16.h"],
+    deps = [
+        ":__support_fputil_cast",
+        ":__support_fputil_nearest_integer_operations",
+        ":__support_macros_config",
+        ":llvm_libc_macros_float16_macros",
+    ],
+)
+
+libc_support_library(
+    name = "__support_math_roundevenl",
+    hdrs = ["src/__support/math/roundevenl.h"],
+    deps = [
+        ":__support_fputil_nearest_integer_operations",
+        ":__support_macros_config",
+    ],
+)
+
+libc_support_library(
+    name = "__support_math_roundf",
+    hdrs = ["src/__support/math/roundf.h"],
+    deps = [
+        ":__support_fputil_nearest_integer_operations",
+        ":__support_macros_config",
+    ],
+)
+
+libc_support_library(
+    name = "__support_math_roundf128",
+    hdrs = ["src/__support/math/roundf128.h"],
+    deps = [
+        ":__support_fputil_nearest_integer_operations",
+        ":__support_macros_config",
+        ":llvm_libc_types_float128",
+    ],
+)
+
+libc_support_library(
+    name = "__support_math_roundf16",
+    hdrs = ["src/__support/math/roundf16.h"],
+    deps = [
+        ":__support_fputil_cast",
+        ":__support_fputil_nearest_integer_operations",
+        ":__support_macros_config",
+        ":llvm_libc_macros_float16_macros",
+    ],
+)
+
+libc_support_library(
+    name = "__support_math_roundl",
+    hdrs = ["src/__support/math/roundl.h"],
+    deps = [
+        ":__support_fputil_nearest_integer_operations",
+        ":__support_macros_config",
+    ],
+)
+
 libc_support_library(
     name = "__support_math_scalbln",
     hdrs = ["src/__support/math/scalbln.h"],
@@ -8453,6 +8569,64 @@ libc_support_library(
     ],
 )
 
+libc_support_library(
+    name = "__support_math_trunc",
+    hdrs = ["src/__support/math/trunc.h"],
+    deps = [
+        ":__support_fputil_nearest_integer_operations",
+        ":__support_macros_config",
+    ],
+)
+
+libc_support_library(
+    name = "__support_math_truncbf16",
+    hdrs = ["src/__support/math/truncbf16.h"],
+    deps = [
+        ":__support_fputil_bfloat16",
+        ":__support_fputil_nearest_integer_operations",
+        ":__support_macros_config",
+    ],
+)
+
+libc_support_library(
+    name = "__support_math_truncf",
+    hdrs = ["src/__support/math/truncf.h"],
+    deps = [
+        ":__support_fputil_nearest_integer_operations",
+        ":__support_macros_config",
+    ],
+)
+
+libc_support_library(
+    name = "__support_math_truncf128",
+    hdrs = ["src/__support/math/truncf128.h"],
+    deps = [
+        ":__support_fputil_nearest_integer_operations",
+        ":__support_macros_config",
+        ":llvm_libc_types_float128",
+    ],
+)
+
+libc_support_library(
+    name = "__support_math_truncf16",
+    hdrs = ["src/__support/math/truncf16.h"],
+    deps = [
+        ":__support_fputil_cast",
+        ":__support_fputil_nearest_integer_operations",
+        ":__support_macros_config",
+        ":llvm_libc_macros_float16_macros",
+    ],
+)
+
+libc_support_library(
+    name = "__support_math_truncl",
+    hdrs = ["src/__support/math/truncl.h"],
+    deps = [
+        ":__support_fputil_nearest_integer_operations",
+        ":__support_macros_config",
+    ],
+)
+
 libc_support_library(
     name = "__support_math_ufromfp",
     hdrs = ["src/__support/math/ufromfp.h"],
@@ -11528,39 +11702,87 @@ libc_math_function(
     ],
 )
 
-libc_math_function(name = "round")
+libc_math_function(
+    name = "round",
+    additional_deps = [
+        ":__support_math_round",
+    ],
+)
+
+libc_math_function(
+    name = "roundbf16",
+    additional_deps = [
+        ":__support_math_roundbf16",
+    ],
+)
+
+libc_math_function(
+    name = "roundevenbf16",
+    additional_deps = [
+        ":__support_math_roundevenbf16",
+    ],
+)
 
-libc_math_function(name = "roundf")
+libc_math_function(
+    name = "roundf",
+    additional_deps = [
+        ":__support_math_roundf",
+    ],
+)
 
-libc_math_function(name = "roundl")
+libc_math_function(
+    name = "roundl",
+    additional_deps = [
+        ":__support_math_roundl",
+    ],
+)
 
 libc_math_function(
     name = "roundf128",
+    additional_deps = [
+        ":__support_math_roundf128",
+    ],
 )
 
 libc_math_function(
     name = "roundf16",
     additional_deps = [
-        ":__support_fputil_cast",
-        ":__support_macros_properties_cpu_features",
+        ":__support_math_roundf16",
     ],
 )
 
-libc_math_function(name = "roundeven")
+libc_math_function(
+    name = "roundeven",
+    additional_deps = [
+        ":__support_math_roundeven",
+    ],
+)
 
-libc_math_function(name = "roundevenf")
+libc_math_function(
+    name = "roundevenf",
+    additional_deps = [
+        ":__support_math_roundevenf",
+    ],
+)
 
-libc_math_function(name = "roundevenl")
+libc_math_function(
+    name = "roundevenl",
+    additional_deps = [
+        ":__support_math_roundevenl",
+    ],
+)
 
 libc_math_function(
     name = "roundevenf128",
+    additional_deps = [
+        ":__support_math_roundevenf128",
+    ],
 )
 
 libc_math_function(
     name = "roundevenf16",
     additional_deps = [
-        ":__support_fputil_cast",
-        ":__support_macros_properties_cpu_features",
+        ":__support_math_roundevenf16",
     ],
 )
 
@@ -11961,21 +12183,45 @@ libc_math_function(
     ],
 )
 
-libc_math_function(name = "trunc")
+libc_math_function(
+    name = "trunc",
+    additional_deps = [
+        ":__support_math_trunc",
+    ],
+)
 
-libc_math_function(name = "truncf")
+libc_math_function(
+    name = "truncbf16",
+    additional_deps = [
+        ":__support_math_truncbf16",
+    ],
+)
 
-libc_math_function(name = "truncl")
+libc_math_function(
+    name = "truncf",
+    additional_deps = [
+        ":__support_math_truncf",
+    ],
+)
+
+libc_math_function(
+    name = "truncl",
+    additional_deps = [
+        ":__support_math_truncl",
+    ],
+)
 
 libc_math_function(
     name = "truncf128",
+    additional_deps = [
+        ":__support_math_truncf128",
+    ],
 )
 
 libc_math_function(
     name = "truncf16",
     additional_deps = [
-        ":__support_fputil_cast",
-        ":__support_macros_properties_cpu_features",
+        ":__support_math_truncf16",
     ],
 )
 

>From d2525ad26ed0cf3993dfbfbbbb57800a1d582412 Mon Sep 17 00:00:00 2001
From: Muhammad Bassiouni <60100307+bassiounix at users.noreply.github.com>
Date: Mon, 4 May 2026 09:26:41 +0300
Subject: [PATCH 2/5] Apply suggestion from @bassiounix

---
 libc/src/__support/math/CMakeLists.txt | 1 +
 libc/src/__support/math/round.h        | 2 +-
 libc/src/__support/math/roundeven.h    | 2 +-
 libc/src/__support/math/roundevenf.h   | 2 +-
 libc/src/__support/math/roundevenf16.h | 2 +-
 libc/src/__support/math/roundf.h       | 2 +-
 libc/src/__support/math/roundf16.h     | 2 +-
 libc/src/__support/math/trunc.h        | 2 +-
 libc/src/__support/math/truncf.h       | 2 +-
 libc/src/__support/math/truncf16.h     | 2 +-
 10 files changed, 10 insertions(+), 9 deletions(-)

diff --git a/libc/src/__support/math/CMakeLists.txt b/libc/src/__support/math/CMakeLists.txt
index dd27e70b903d3..44bf714418903 100644
--- a/libc/src/__support/math/CMakeLists.txt
+++ b/libc/src/__support/math/CMakeLists.txt
@@ -2390,6 +2390,7 @@ add_header_library(
   FLAGS
     ROUND_OPT
 )
+
 add_header_library(
   roundeven
   HDRS
diff --git a/libc/src/__support/math/round.h b/libc/src/__support/math/round.h
index 5bf356974f455..4fa4084d1b98b 100644
--- a/libc/src/__support/math/round.h
+++ b/libc/src/__support/math/round.h
@@ -15,7 +15,7 @@
 namespace LIBC_NAMESPACE_DECL {
 namespace math {
 
-LIBC_INLINE constexpr double round(double x) {
+LIBC_INLINE LIBC_CONSTEXPR double round(double x) {
 #if defined(__LIBC_USE_BUILTIN_ROUND) && !defined(LIBC_HAS_CONSTANT_EVALUATION)
   return __builtin_round(x);
 #else
diff --git a/libc/src/__support/math/roundeven.h b/libc/src/__support/math/roundeven.h
index d26b5384d2dc1..805e1e538a289 100644
--- a/libc/src/__support/math/roundeven.h
+++ b/libc/src/__support/math/roundeven.h
@@ -15,7 +15,7 @@
 namespace LIBC_NAMESPACE_DECL {
 namespace math {
 
-LIBC_INLINE constexpr double roundeven(double x) {
+LIBC_INLINE LIBC_CONSTEXPR double roundeven(double x) {
 #if defined(__LIBC_USE_BUILTIN_ROUNDEVEN) &&                                   \
     !defined(LIBC_HAS_CONSTANT_EVALUATION)
   return __builtin_roundeven(x);
diff --git a/libc/src/__support/math/roundevenf.h b/libc/src/__support/math/roundevenf.h
index 2af77270d0a6c..662b1308cbbb1 100644
--- a/libc/src/__support/math/roundevenf.h
+++ b/libc/src/__support/math/roundevenf.h
@@ -15,7 +15,7 @@
 namespace LIBC_NAMESPACE_DECL {
 namespace math {
 
-LIBC_INLINE constexpr float roundevenf(float x) {
+LIBC_INLINE LIBC_CONSTEXPR float roundevenf(float x) {
 #if defined(__LIBC_USE_BUILTIN_ROUNDEVEN) &&                                   \
     !defined(LIBC_HAS_CONSTANT_EVALUATION)
   return __builtin_roundevenf(x);
diff --git a/libc/src/__support/math/roundevenf16.h b/libc/src/__support/math/roundevenf16.h
index 6be3086ff4e9b..a8f8967f15b90 100644
--- a/libc/src/__support/math/roundevenf16.h
+++ b/libc/src/__support/math/roundevenf16.h
@@ -21,7 +21,7 @@
 namespace LIBC_NAMESPACE_DECL {
 namespace math {
 
-LIBC_INLINE constexpr float16 roundevenf16(float16 x) {
+LIBC_INLINE LIBC_CONSTEXPR float16 roundevenf16(float16 x) {
 #if defined(__LIBC_USE_BUILTIN_ROUNDEVEN) &&                                   \
     defined(LIBC_TARGET_CPU_HAS_FAST_FLOAT16_OPS) &&                           \
     !defined(LIBC_HAS_CONSTANT_EVALUATION)
diff --git a/libc/src/__support/math/roundf.h b/libc/src/__support/math/roundf.h
index 94ce6deb6f81a..339d3af23992d 100644
--- a/libc/src/__support/math/roundf.h
+++ b/libc/src/__support/math/roundf.h
@@ -15,7 +15,7 @@
 namespace LIBC_NAMESPACE_DECL {
 namespace math {
 
-LIBC_INLINE constexpr float roundf(float x) {
+LIBC_INLINE LIBC_CONSTEXPR float roundf(float x) {
 #if defined(__LIBC_USE_BUILTIN_ROUND) && !defined(LIBC_HAS_CONSTANT_EVALUATION)
   return __builtin_roundf(x);
 #else
diff --git a/libc/src/__support/math/roundf16.h b/libc/src/__support/math/roundf16.h
index e525d80d6be53..b6ffbeff38e64 100644
--- a/libc/src/__support/math/roundf16.h
+++ b/libc/src/__support/math/roundf16.h
@@ -21,7 +21,7 @@
 namespace LIBC_NAMESPACE_DECL {
 namespace math {
 
-LIBC_INLINE constexpr float16 roundf16(float16 x) {
+LIBC_INLINE LIBC_CONSTEXPR float16 roundf16(float16 x) {
 #if defined(__LIBC_USE_BUILTIN_ROUND) &&                                       \
     defined(LIBC_TARGET_CPU_HAS_FAST_FLOAT16_OPS) &&                           \
     !defined(LIBC_HAS_CONSTANT_EVALUATION)
diff --git a/libc/src/__support/math/trunc.h b/libc/src/__support/math/trunc.h
index 2a8c6c739a9af..e54563cfc3876 100644
--- a/libc/src/__support/math/trunc.h
+++ b/libc/src/__support/math/trunc.h
@@ -15,7 +15,7 @@
 namespace LIBC_NAMESPACE_DECL {
 namespace math {
 
-LIBC_INLINE constexpr double trunc(double x) {
+LIBC_INLINE LIBC_CONSTEXPR double trunc(double x) {
 #if defined(__LIBC_USE_BUILTIN_CEIL_FLOOR_RINT_TRUNC) &&                       \
     !defined(LIBC_HAS_CONSTANT_EVALUATION)
   return __builtin_trunc(x);
diff --git a/libc/src/__support/math/truncf.h b/libc/src/__support/math/truncf.h
index bf6b529b68de9..32a1eeeaec049 100644
--- a/libc/src/__support/math/truncf.h
+++ b/libc/src/__support/math/truncf.h
@@ -15,7 +15,7 @@
 namespace LIBC_NAMESPACE_DECL {
 namespace math {
 
-LIBC_INLINE constexpr float truncf(float x) {
+LIBC_INLINE LIBC_CONSTEXPR float truncf(float x) {
 #if defined(__LIBC_USE_BUILTIN_CEIL_FLOOR_RINT_TRUNC) &&                       \
     !defined(LIBC_HAS_CONSTANT_EVALUATION)
   return __builtin_truncf(x);
diff --git a/libc/src/__support/math/truncf16.h b/libc/src/__support/math/truncf16.h
index 5e2721a8318ad..46c90876f86b7 100644
--- a/libc/src/__support/math/truncf16.h
+++ b/libc/src/__support/math/truncf16.h
@@ -21,7 +21,7 @@
 namespace LIBC_NAMESPACE_DECL {
 namespace math {
 
-LIBC_INLINE constexpr float16 truncf16(float16 x) {
+LIBC_INLINE LIBC_CONSTEXPR float16 truncf16(float16 x) {
 #if defined(__LIBC_USE_BUILTIN_CEIL_FLOOR_RINT_TRUNC) &&                       \
     defined(LIBC_TARGET_CPU_HAS_FAST_FLOAT16_OPS) &&                           \
     !defined(LIBC_HAS_CONSTANT_EVALUATION)

>From f030ca8e930a02564ae23e1891d789e0ddd2d8df Mon Sep 17 00:00:00 2001
From: Muhammad Bassiouni <60100307+bassiounix at users.noreply.github.com>
Date: Mon, 4 May 2026 09:27:13 +0300
Subject: [PATCH 3/5] Apply suggestion from @bassiounix

---
 libc/src/__support/math/CMakeLists.txt | 1 -
 1 file changed, 1 deletion(-)

diff --git a/libc/src/__support/math/CMakeLists.txt b/libc/src/__support/math/CMakeLists.txt
index 44bf714418903..38c451c6cdb1b 100644
--- a/libc/src/__support/math/CMakeLists.txt
+++ b/libc/src/__support/math/CMakeLists.txt
@@ -2457,7 +2457,6 @@ add_header_library(
     libc.src.__support.macros.config
 )
 
-
 add_header_library(
   roundf
   HDRS

>From b39973150e66d15e212b32e37ec7d1192c75af72 Mon Sep 17 00:00:00 2001
From: Muhammad Bassiouni <60100307+bassiounix at users.noreply.github.com>
Date: Mon, 4 May 2026 09:28:00 +0300
Subject: [PATCH 4/5] Apply suggestion from @bassiounix

---
 libc/src/__support/math/CMakeLists.txt | 1 -
 1 file changed, 1 deletion(-)

diff --git a/libc/src/__support/math/CMakeLists.txt b/libc/src/__support/math/CMakeLists.txt
index 38c451c6cdb1b..32a85c291d628 100644
--- a/libc/src/__support/math/CMakeLists.txt
+++ b/libc/src/__support/math/CMakeLists.txt
@@ -5594,7 +5594,6 @@ add_header_library(
     libc.src.__support.macros.config
 )
 
-
 add_header_library(
   ufromfp
   HDRS

>From 76267f091a76d214eba2c5105cc4d7c027afea22 Mon Sep 17 00:00:00 2001
From: Anonmiraj <ezzibrahimx at gmail.com>
Date: Mon, 4 May 2026 10:14:03 +0300
Subject: [PATCH 5/5] add missing bazel debs

---
 utils/bazel/llvm-project-overlay/libc/BUILD.bazel | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/utils/bazel/llvm-project-overlay/libc/BUILD.bazel b/utils/bazel/llvm-project-overlay/libc/BUILD.bazel
index cad1fc4e8b3d3..6bb1c47c06d98 100644
--- a/utils/bazel/llvm-project-overlay/libc/BUILD.bazel
+++ b/utils/bazel/llvm-project-overlay/libc/BUILD.bazel
@@ -5614,6 +5614,7 @@ libc_support_library(
         ":__support_fputil_cast",
         ":__support_fputil_nearest_integer_operations",
         ":__support_macros_config",
+        ":__support_macros_properties_cpu_features",
         ":llvm_libc_macros_float16_macros",
     ],
 )
@@ -5653,6 +5654,7 @@ libc_support_library(
         ":__support_fputil_cast",
         ":__support_fputil_nearest_integer_operations",
         ":__support_macros_config",
+        ":__support_macros_properties_cpu_features",
         ":llvm_libc_macros_float16_macros",
     ],
 )
@@ -8614,6 +8616,7 @@ libc_support_library(
         ":__support_fputil_cast",
         ":__support_fputil_nearest_integer_operations",
         ":__support_macros_config",
+        ":__support_macros_properties_cpu_features",
         ":llvm_libc_macros_float16_macros",
     ],
 )



More information about the libc-commits mailing list