[libc-commits] [libc] [libc][builtins] add cmp_helper for compiler-rt soft-float comparisons (PR #212649)

via libc-commits libc-commits at lists.llvm.org
Sat Aug 8 14:41:31 PDT 2026


https://github.com/hulxv updated https://github.com/llvm/llvm-project/pull/212649

>From f7f9530c089e3a016898e3eb3fc025d7d469e18b Mon Sep 17 00:00:00 2001
From: hulxv <hulxxv at gmail.com>
Date: Wed, 29 Jul 2026 00:28:43 +0300
Subject: [PATCH 1/2] [libc][builtins] add cmp_helper for compiler-rt
 soft-float comparisons

---
 libc/src/__support/builtins/CMakeLists.txt |  7 +++
 libc/src/__support/builtins/cmp_helper.h   | 63 ++++++++++++++++++++++
 2 files changed, 70 insertions(+)
 create mode 100644 libc/src/__support/builtins/cmp_helper.h

diff --git a/libc/src/__support/builtins/CMakeLists.txt b/libc/src/__support/builtins/CMakeLists.txt
index a3e6303f09169..aa3afaf190304 100644
--- a/libc/src/__support/builtins/CMakeLists.txt
+++ b/libc/src/__support/builtins/CMakeLists.txt
@@ -232,6 +232,13 @@ add_header_library(
     truncdfsf2.h
   DEPENDS
     libc.src.__support.builtins.fpconvert_helper
+  cmp_helper
+  HDRS
+    cmp_helper.h
+  DEPENDS
+    libc.src.__support.FPUtil.comparison_operations
+    libc.src.__support.FPUtil.fp_bits
+    libc.src.__support.macros.attributes
     libc.src.__support.macros.config
 )
 
diff --git a/libc/src/__support/builtins/cmp_helper.h b/libc/src/__support/builtins/cmp_helper.h
new file mode 100644
index 0000000000000..6616783cfc3e4
--- /dev/null
+++ b/libc/src/__support/builtins/cmp_helper.h
@@ -0,0 +1,63 @@
+//===----------------------------------------------------------------------===//
+//
+// 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
+//
+//===----------------------------------------------------------------------===//
+///
+/// \file
+/// Shared floating-point comparison results for compiler-rt's soft-float
+/// compare builtins.  These mirror compiler-rt's GCC-compatible __le<f>2 /
+/// __ge<f>2 / __unord<f>2 (quiet: they raise no FP exceptions), reusing
+/// LLVM-libc's IEEE comparison predicates, so they can be reused by
+/// compiler-rt's builtins.
+///
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_LIBC_SRC___SUPPORT_BUILTINS_CMP_HELPER_H
+#define LLVM_LIBC_SRC___SUPPORT_BUILTINS_CMP_HELPER_H
+
+#include "src/__support/FPUtil/FPBits.h"
+#include "src/__support/FPUtil/comparison_operations.h"
+#include "src/__support/macros/attributes.h"
+#include "src/__support/macros/config.h"
+
+namespace LIBC_NAMESPACE_DECL {
+namespace builtins {
+
+// GCC soft-float compare, "LE" convention: -1 if a<b, 0 if a==b, 1 if a>b, and
+// 1 when unordered (either operand is NaN).  Quiet -- raises no FP exceptions,
+// matching compiler-rt's __le<f>2 (which __eq/__ne/__lt/__cmp alias).  NaN is
+// handled up front so the ordering predicates are only reached for non-NaN
+// inputs, where they never signal.
+template <typename T> LIBC_INLINE int cmp_le(T a, T b) {
+  using FPBits = fputil::FPBits<T>;
+  if (FPBits(a).is_nan() || FPBits(b).is_nan())
+    return 1; // LE_UNORDERED
+  if (fputil::equals(a, b))
+    return 0; // LE_EQUAL
+  return fputil::less_than(a, b) ? -1 : 1; // LE_LESS : LE_GREATER
+}
+
+// Same as cmp_le, but unordered yields -1; matches compiler-rt's __ge<f>2
+// (which __gt aliases).
+template <typename T> LIBC_INLINE int cmp_ge(T a, T b) {
+  using FPBits = fputil::FPBits<T>;
+  if (FPBits(a).is_nan() || FPBits(b).is_nan())
+    return -1; // GE_UNORDERED
+  if (fputil::equals(a, b))
+    return 0; // GE_EQUAL
+  return fputil::greater_than(a, b) ? 1 : -1; // GE_GREATER : GE_LESS
+}
+
+// 1 iff either operand is NaN, else 0; matches compiler-rt's __unord<f>2.
+template <typename T> LIBC_INLINE int cmp_unord(T a, T b) {
+  using FPBits = fputil::FPBits<T>;
+  return FPBits(a).is_nan() || FPBits(b).is_nan();
+}
+
+} // namespace builtins
+} // namespace LIBC_NAMESPACE_DECL
+
+#endif // LLVM_LIBC_SRC___SUPPORT_BUILTINS_CMP_HELPER_H

>From 17a487e2886361247d5b76afb08c1e3b809b6c50 Mon Sep 17 00:00:00 2001
From: hulxv <hulxxv at gmail.com>
Date: Wed, 29 Jul 2026 02:14:36 +0300
Subject: [PATCH 2/2] fix format

---
 libc/src/__support/builtins/cmp_helper.h | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/libc/src/__support/builtins/cmp_helper.h b/libc/src/__support/builtins/cmp_helper.h
index 6616783cfc3e4..7cbfb70287f59 100644
--- a/libc/src/__support/builtins/cmp_helper.h
+++ b/libc/src/__support/builtins/cmp_helper.h
@@ -36,7 +36,7 @@ template <typename T> LIBC_INLINE int cmp_le(T a, T b) {
   if (FPBits(a).is_nan() || FPBits(b).is_nan())
     return 1; // LE_UNORDERED
   if (fputil::equals(a, b))
-    return 0; // LE_EQUAL
+    return 0;                              // LE_EQUAL
   return fputil::less_than(a, b) ? -1 : 1; // LE_LESS : LE_GREATER
 }
 
@@ -47,7 +47,7 @@ template <typename T> LIBC_INLINE int cmp_ge(T a, T b) {
   if (FPBits(a).is_nan() || FPBits(b).is_nan())
     return -1; // GE_UNORDERED
   if (fputil::equals(a, b))
-    return 0; // GE_EQUAL
+    return 0;                                 // GE_EQUAL
   return fputil::greater_than(a, b) ? 1 : -1; // GE_GREATER : GE_LESS
 }
 



More information about the libc-commits mailing list