Skip to content

[libc] implement stdc_leading_zeros_u* for stdbit.h #79669

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 10 commits into from
Jan 29, 2024

Conversation

nickdesaulniers
Copy link
Member

  • stdbit.stdc_leading_zeros_uc
  • stdbit.stdc_leading_zeros_us
  • stdbit.stdc_leading_zeros_ui
  • stdbit.stdc_leading_zeros_ul
  • stdbit.stdc_leading_zeros_ull

Test via:
$ ninja libc-stdbit-tests libc_include_tests

- stdbit.stdc_leading_zeros_uc
- stdbit.stdc_leading_zeros_us
- stdbit.stdc_leading_zeros_ui
- stdbit.stdc_leading_zeros_ul
- stdbit.stdc_leading_zeros_ull

Test via:
$ ninja libc-stdbit-tests libc_include_tests
@llvmbot llvmbot added the libc label Jan 27, 2024
@llvmbot
Copy link
Member

llvmbot commented Jan 27, 2024

@llvm/pr-subscribers-libc

Author: Nick Desaulniers (nickdesaulniers)

Changes
  • stdbit.stdc_leading_zeros_uc
  • stdbit.stdc_leading_zeros_us
  • stdbit.stdc_leading_zeros_ui
  • stdbit.stdc_leading_zeros_ul
  • stdbit.stdc_leading_zeros_ull

Test via:
$ ninja libc-stdbit-tests libc_include_tests


Patch is 25.53 KiB, truncated to 20.00 KiB below, full version: https://github.com/llvm/llvm-project/pull/79669.diff

29 Files Affected:

  • (modified) libc/config/linux/x86_64/entrypoints.txt (+7)
  • (modified) libc/config/linux/x86_64/headers.txt (+1)
  • (modified) libc/include/CMakeLists.txt (+9)
  • (modified) libc/include/llvm-libc-macros/CMakeLists.txt (+6)
  • (added) libc/include/llvm-libc-macros/stdbit-macros.h (+19)
  • (added) libc/include/stdbit.h.def (+17)
  • (modified) libc/spec/spec.td (+1)
  • (modified) libc/spec/stdc.td (+18-1)
  • (modified) libc/src/CMakeLists.txt (+3-2)
  • (added) libc/src/stdbit/CMakeLists.txt (+39)
  • (added) libc/src/stdbit/stdc_leading_zeros_uc.cpp (+20)
  • (added) libc/src/stdbit/stdc_leading_zeros_uc.h (+18)
  • (added) libc/src/stdbit/stdc_leading_zeros_ui.cpp (+20)
  • (added) libc/src/stdbit/stdc_leading_zeros_ui.h (+18)
  • (added) libc/src/stdbit/stdc_leading_zeros_ul.cpp (+20)
  • (added) libc/src/stdbit/stdc_leading_zeros_ul.h (+18)
  • (added) libc/src/stdbit/stdc_leading_zeros_ull.cpp (+20)
  • (added) libc/src/stdbit/stdc_leading_zeros_ull.h (+18)
  • (added) libc/src/stdbit/stdc_leading_zeros_us.cpp (+20)
  • (added) libc/src/stdbit/stdc_leading_zeros_us.h (+18)
  • (modified) libc/test/include/CMakeLists.txt (+19)
  • (added) libc/test/include/stdbit_test.cpp (+22)
  • (modified) libc/test/src/CMakeLists.txt (+6-5)
  • (added) libc/test/src/stdbit/CMakeLists.txt (+51)
  • (added) libc/test/src/stdbit/stdc_leading_zeros_uc_test.cpp (+22)
  • (added) libc/test/src/stdbit/stdc_leading_zeros_ui_test.cpp (+23)
  • (added) libc/test/src/stdbit/stdc_leading_zeros_ul_test.cpp (+23)
  • (added) libc/test/src/stdbit/stdc_leading_zeros_ull_test.cpp (+24)
  • (added) libc/test/src/stdbit/stdc_leading_zeros_us_test.cpp (+22)
diff --git a/libc/config/linux/x86_64/entrypoints.txt b/libc/config/linux/x86_64/entrypoints.txt
index 3812d9586121e7d..e714f0f6cc5ac51 100644
--- a/libc/config/linux/x86_64/entrypoints.txt
+++ b/libc/config/linux/x86_64/entrypoints.txt
@@ -91,6 +91,13 @@ set(TARGET_LIBC_ENTRYPOINTS
     libc.src.inttypes.strtoimax
     libc.src.inttypes.strtoumax
 
+    # stdbit.h entrypoints
+    libc.src.stdbit.stdc_leading_zeros_uc
+    libc.src.stdbit.stdc_leading_zeros_us
+    libc.src.stdbit.stdc_leading_zeros_ui
+    libc.src.stdbit.stdc_leading_zeros_ul
+    libc.src.stdbit.stdc_leading_zeros_ull
+
     # stdlib.h entrypoints
     libc.src.stdlib.abs
     libc.src.stdlib.atoi
diff --git a/libc/config/linux/x86_64/headers.txt b/libc/config/linux/x86_64/headers.txt
index d103176897a74a8..4009501bc45ce8a 100644
--- a/libc/config/linux/x86_64/headers.txt
+++ b/libc/config/linux/x86_64/headers.txt
@@ -15,6 +15,7 @@ set(TARGET_PUBLIC_HEADERS
     libc.include.signal
     libc.include.spawn
     libc.include.setjmp
+    libc.include.stdbit
     libc.include.stdio
     libc.include.stdlib
     libc.include.string
diff --git a/libc/include/CMakeLists.txt b/libc/include/CMakeLists.txt
index 89fffd1022758ea..9474bdd3791264d 100644
--- a/libc/include/CMakeLists.txt
+++ b/libc/include/CMakeLists.txt
@@ -223,6 +223,15 @@ else()
   message(STATUS "Skipping header signal.h as the target config is missing")
 endif()
 
+add_gen_header(
+  stdbit
+  DEF_FILE stdbit.h.def
+  GEN_HDR stdbit.h
+  DEPENDS
+    .llvm_libc_common_h
+    .llvm-libc-macros.stdbit_macros
+)
+
 add_gen_header(
   stdio
   DEF_FILE stdio.h.def
diff --git a/libc/include/llvm-libc-macros/CMakeLists.txt b/libc/include/llvm-libc-macros/CMakeLists.txt
index 96ee29d7327224c..c5a7e742cadd138 100644
--- a/libc/include/llvm-libc-macros/CMakeLists.txt
+++ b/libc/include/llvm-libc-macros/CMakeLists.txt
@@ -111,6 +111,12 @@ add_macro_header(
     signal-macros.h
 )
 
+add_macro_header(
+  stdbit_macros
+  HDR
+    stdbit-macros.h
+)
+
 add_macro_header(
   stdio_macros
   HDR
diff --git a/libc/include/llvm-libc-macros/stdbit-macros.h b/libc/include/llvm-libc-macros/stdbit-macros.h
new file mode 100644
index 000000000000000..183328877c3da89
--- /dev/null
+++ b/libc/include/llvm-libc-macros/stdbit-macros.h
@@ -0,0 +1,19 @@
+//===-- Definition of macros to be used with stdbit functions ----------===//
+//
+// 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_MACROS_STDBIT_MACROS_H
+#define __LLVM_LIBC_MACROS_STDBIT_MACROS_H
+
+#define stdc_leading_zeros(x) _Generic((x), \
+  unsigned char: stdc_leading_zeros_uc, \
+  unsigned short: stdc_leading_zeros_us, \
+  unsigned: stdc_leading_zeros_ui, \
+  unsigned long: stdc_leading_zeros_ul, \
+  unsigned long long: stdc_leading_zeros_ull)(x)
+
+#endif // __LLVM_LIBC_MACROS_STDBIT_MACROS_H
diff --git a/libc/include/stdbit.h.def b/libc/include/stdbit.h.def
new file mode 100644
index 000000000000000..cb79ac1caf049fd
--- /dev/null
+++ b/libc/include/stdbit.h.def
@@ -0,0 +1,17 @@
+//===-- C standard library header stdbit.h --------------------------------===//
+//
+// 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_STDBIT_H
+#define LLVM_LIBC_STDBIT_H
+
+#include <__llvm-libc-common.h>
+#include <llvm-libc-macros/stdbit-macros.h>
+
+%%public_api()
+
+#endif // LLVM_LIBC_STDBIT_H
diff --git a/libc/spec/spec.td b/libc/spec/spec.td
index 818cfaee6b61c2b..16abf97bf0b1cb4 100644
--- a/libc/spec/spec.td
+++ b/libc/spec/spec.td
@@ -50,6 +50,7 @@ def DoubleType : NamedType<"double">;
 def LongDoubleType : NamedType<"long double">;
 def CharType : NamedType<"char">;
 def UnsignedCharType : NamedType<"unsigned char">;
+def UnsignedShortType : NamedType<"unsigned short">;
 
 // TODO: Add compatibility layer to use C23 type _Float128 if possible.
 def Float128Type : NamedType<"__float128">;
diff --git a/libc/spec/stdc.td b/libc/spec/stdc.td
index 43b81c4abaa0e6b..b21f620d0766af6 100644
--- a/libc/spec/stdc.td
+++ b/libc/spec/stdc.td
@@ -767,6 +767,22 @@ def StdC : StandardSpec<"stdc"> {
       ]
   >;
 
+  HeaderSpec StdBit = HeaderSpec<
+      "stdbit.h",
+      [
+        Macro<"stdc_leading_zeros">
+      ], // Macros
+      [], // Types
+      [], // Enumerations
+      [
+          FunctionSpec<"stdc_leading_zeros_uc", RetValSpec<UnsignedCharType>, [ArgSpec<UnsignedCharType>]>,
+          FunctionSpec<"stdc_leading_zeros_us", RetValSpec<UnsignedShortType>, [ArgSpec<UnsignedShortType>]>,
+          FunctionSpec<"stdc_leading_zeros_ui", RetValSpec<UnsignedIntType>, [ArgSpec<UnsignedIntType>]>,
+          FunctionSpec<"stdc_leading_zeros_ul", RetValSpec<UnsignedLongType>, [ArgSpec<UnsignedLongType>]>,
+          FunctionSpec<"stdc_leading_zeros_ull", RetValSpec<UnsignedLongLongType>, [ArgSpec<UnsignedLongLongType>]>
+      ] // Functions
+  >;
+
   HeaderSpec StdLib = HeaderSpec<
       "stdlib.h",
       [], // Macros
@@ -1141,7 +1157,7 @@ def StdC : StandardSpec<"stdc"> {
       "wchar.h",
       [ // Macros
         Macro<"WEOF">,
-      ], 
+      ],
       [ //Types
         SizeTType,
         WIntType,
@@ -1167,6 +1183,7 @@ def StdC : StandardSpec<"stdc"> {
     Limits,
     Math,
     String,
+    StdBit,
     StdIO,
     StdLib,
     IntTypes,
diff --git a/libc/src/CMakeLists.txt b/libc/src/CMakeLists.txt
index 492f9c5bd50f9bc..5211db7bc1f993e 100644
--- a/libc/src/CMakeLists.txt
+++ b/libc/src/CMakeLists.txt
@@ -5,9 +5,10 @@ add_subdirectory(errno)
 add_subdirectory(fenv)
 add_subdirectory(inttypes)
 add_subdirectory(math)
-add_subdirectory(string)
-add_subdirectory(stdlib)
+add_subdirectory(stdbit)
 add_subdirectory(stdio)
+add_subdirectory(stdlib)
+add_subdirectory(string)
 add_subdirectory(wchar)
 
 if(${LIBC_TARGET_OS} STREQUAL "linux")
diff --git a/libc/src/stdbit/CMakeLists.txt b/libc/src/stdbit/CMakeLists.txt
new file mode 100644
index 000000000000000..5747a8c2f353181
--- /dev/null
+++ b/libc/src/stdbit/CMakeLists.txt
@@ -0,0 +1,39 @@
+add_entrypoint_object(
+  stdc_leading_zeros_uc
+  SRCS
+    stdc_leading_zeros_uc.cpp
+  HDRS
+    stdc_leading_zeros_uc.h
+)
+
+add_entrypoint_object(
+  stdc_leading_zeros_us
+  SRCS
+    stdc_leading_zeros_us.cpp
+  HDRS
+    stdc_leading_zeros_us.h
+)
+
+add_entrypoint_object(
+  stdc_leading_zeros_ui
+  SRCS
+    stdc_leading_zeros_ui.cpp
+  HDRS
+    stdc_leading_zeros_ui.h
+)
+
+add_entrypoint_object(
+  stdc_leading_zeros_ul
+  SRCS
+    stdc_leading_zeros_ul.cpp
+  HDRS
+    stdc_leading_zeros_ul.h
+)
+
+add_entrypoint_object(
+  stdc_leading_zeros_ull
+  SRCS
+    stdc_leading_zeros_ull.cpp
+  HDRS
+    stdc_leading_zeros_ull.h
+)
diff --git a/libc/src/stdbit/stdc_leading_zeros_uc.cpp b/libc/src/stdbit/stdc_leading_zeros_uc.cpp
new file mode 100644
index 000000000000000..a985700274d2594
--- /dev/null
+++ b/libc/src/stdbit/stdc_leading_zeros_uc.cpp
@@ -0,0 +1,20 @@
+//===-- Implementation of stdc_leading_zeros_uc ---------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "src/stdbit/stdc_leading_zeros_uc.h"
+
+#include "src/__support/CPP/bit.h"
+#include "src/__support/common.h"
+
+namespace LIBC_NAMESPACE {
+
+LLVM_LIBC_FUNCTION(unsigned char, stdc_leading_zeros_uc, (unsigned char value)) {
+  return static_cast<unsigned char>(cpp::countl_zero(value));
+}
+
+} // namespace LIBC_NAMESPACE
diff --git a/libc/src/stdbit/stdc_leading_zeros_uc.h b/libc/src/stdbit/stdc_leading_zeros_uc.h
new file mode 100644
index 000000000000000..0622e72b0683ee2
--- /dev/null
+++ b/libc/src/stdbit/stdc_leading_zeros_uc.h
@@ -0,0 +1,18 @@
+//===-- Implementation header for stdc_leading_zeros_uc ---------*- 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_STDBIT_STDC_LEADING_ZEROS_UC_H
+#define LLVM_LIBC_SRC_STDBIT_STDC_LEADING_ZEROS_UC_H
+
+namespace LIBC_NAMESPACE {
+
+unsigned char stdc_leading_zeros_uc(unsigned char value);
+
+} // namespace LIBC_NAMESPACE
+
+#endif // LLVM_LIBC_SRC_STDBIT_STDC_LEADING_ZEROS_UC_H
diff --git a/libc/src/stdbit/stdc_leading_zeros_ui.cpp b/libc/src/stdbit/stdc_leading_zeros_ui.cpp
new file mode 100644
index 000000000000000..99bc0eb70f33bf7
--- /dev/null
+++ b/libc/src/stdbit/stdc_leading_zeros_ui.cpp
@@ -0,0 +1,20 @@
+//===-- Implementation of stdc_leading_zeros_ui ---------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "src/stdbit/stdc_leading_zeros_ui.h"
+
+#include "src/__support/CPP/bit.h"
+#include "src/__support/common.h"
+
+namespace LIBC_NAMESPACE {
+
+LLVM_LIBC_FUNCTION(unsigned, stdc_leading_zeros_ui, (unsigned value)) {
+  return static_cast<unsigned>(cpp::countl_zero(value));
+}
+
+} // namespace LIBC_NAMESPACE
diff --git a/libc/src/stdbit/stdc_leading_zeros_ui.h b/libc/src/stdbit/stdc_leading_zeros_ui.h
new file mode 100644
index 000000000000000..14113d486b54a0f
--- /dev/null
+++ b/libc/src/stdbit/stdc_leading_zeros_ui.h
@@ -0,0 +1,18 @@
+//===-- Implementation header for stdc_leading_zeros_ui ---------*- 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_STDBIT_STDC_LEADING_ZEROS_UI_H
+#define LLVM_LIBC_SRC_STDBIT_STDC_LEADING_ZEROS_UI_H
+
+namespace LIBC_NAMESPACE {
+
+unsigned stdc_leading_zeros_ui(unsigned value);
+
+} // namespace LIBC_NAMESPACE
+
+#endif // LLVM_LIBC_SRC_STDBIT_STDC_LEADING_ZEROS_UI_H
diff --git a/libc/src/stdbit/stdc_leading_zeros_ul.cpp b/libc/src/stdbit/stdc_leading_zeros_ul.cpp
new file mode 100644
index 000000000000000..4ce56be04ff358e
--- /dev/null
+++ b/libc/src/stdbit/stdc_leading_zeros_ul.cpp
@@ -0,0 +1,20 @@
+//===-- Implementation of stdc_leading_zeros_ul ---------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "src/stdbit/stdc_leading_zeros_ul.h"
+
+#include "src/__support/CPP/bit.h"
+#include "src/__support/common.h"
+
+namespace LIBC_NAMESPACE {
+
+LLVM_LIBC_FUNCTION(unsigned long, stdc_leading_zeros_ul, (unsigned long value)) {
+  return static_cast<unsigned long>(cpp::countl_zero(value));
+}
+
+} // namespace LIBC_NAMESPACE
diff --git a/libc/src/stdbit/stdc_leading_zeros_ul.h b/libc/src/stdbit/stdc_leading_zeros_ul.h
new file mode 100644
index 000000000000000..a1f36299931dc2b
--- /dev/null
+++ b/libc/src/stdbit/stdc_leading_zeros_ul.h
@@ -0,0 +1,18 @@
+//===-- Implementation header for stdc_leading_zeros_ul ---------*- 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_STDBIT_STDC_LEADING_ZEROS_UL_H
+#define LLVM_LIBC_SRC_STDBIT_STDC_LEADING_ZEROS_UL_H
+
+namespace LIBC_NAMESPACE {
+
+unsigned long stdc_leading_zeros_ul(unsigned long value);
+
+} // namespace LIBC_NAMESPACE
+
+#endif // LLVM_LIBC_SRC_STDBIT_STDC_LEADING_ZEROS_UL_H
diff --git a/libc/src/stdbit/stdc_leading_zeros_ull.cpp b/libc/src/stdbit/stdc_leading_zeros_ull.cpp
new file mode 100644
index 000000000000000..5abd6a6e7aab9f7
--- /dev/null
+++ b/libc/src/stdbit/stdc_leading_zeros_ull.cpp
@@ -0,0 +1,20 @@
+//===-- Implementation of stdc_leading_zeros_ull --------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "src/stdbit/stdc_leading_zeros_ull.h"
+
+#include "src/__support/CPP/bit.h"
+#include "src/__support/common.h"
+
+namespace LIBC_NAMESPACE {
+
+LLVM_LIBC_FUNCTION(unsigned long long, stdc_leading_zeros_ull, (unsigned long long value)) {
+  return static_cast<unsigned long long>(cpp::countl_zero(value));
+}
+
+} // namespace LIBC_NAMESPACE
diff --git a/libc/src/stdbit/stdc_leading_zeros_ull.h b/libc/src/stdbit/stdc_leading_zeros_ull.h
new file mode 100644
index 000000000000000..b05855b296af0b9
--- /dev/null
+++ b/libc/src/stdbit/stdc_leading_zeros_ull.h
@@ -0,0 +1,18 @@
+//===-- Implementation header for stdc_leading_zeros_ull --------*- 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_STDBIT_STDC_LEADING_ZEROS_ULL_H
+#define LLVM_LIBC_SRC_STDBIT_STDC_LEADING_ZEROS_ULL_H
+
+namespace LIBC_NAMESPACE {
+
+unsigned long long stdc_leading_zeros_ull(unsigned long long value);
+
+} // namespace LIBC_NAMESPACE
+
+#endif // LLVM_LIBC_SRC_STDBIT_STDC_LEADING_ZEROS_ULL_H
diff --git a/libc/src/stdbit/stdc_leading_zeros_us.cpp b/libc/src/stdbit/stdc_leading_zeros_us.cpp
new file mode 100644
index 000000000000000..0c14d5374a97373
--- /dev/null
+++ b/libc/src/stdbit/stdc_leading_zeros_us.cpp
@@ -0,0 +1,20 @@
+//===-- Implementation of stdc_leading_zeros_us ---------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "src/stdbit/stdc_leading_zeros_us.h"
+
+#include "src/__support/CPP/bit.h"
+#include "src/__support/common.h"
+
+namespace LIBC_NAMESPACE {
+
+LLVM_LIBC_FUNCTION(unsigned short, stdc_leading_zeros_us, (unsigned short value)) {
+  return static_cast<unsigned short>(cpp::countl_zero(value));
+}
+
+} // namespace LIBC_NAMESPACE
diff --git a/libc/src/stdbit/stdc_leading_zeros_us.h b/libc/src/stdbit/stdc_leading_zeros_us.h
new file mode 100644
index 000000000000000..c0f62e2be2f02b4
--- /dev/null
+++ b/libc/src/stdbit/stdc_leading_zeros_us.h
@@ -0,0 +1,18 @@
+//===-- Implementation header for stdc_leading_zeros_us ---------*- 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_STDBIT_STDC_LEADING_ZEROS_US_H
+#define LLVM_LIBC_SRC_STDBIT_STDC_LEADING_ZEROS_US_H
+
+namespace LIBC_NAMESPACE {
+
+unsigned short stdc_leading_zeros_us(unsigned short value);
+
+} // namespace LIBC_NAMESPACE
+
+#endif // LLVM_LIBC_SRC_STDBIT_STDC_LEADING_ZEROS_US_H
diff --git a/libc/test/include/CMakeLists.txt b/libc/test/include/CMakeLists.txt
index 183e7ecde719e55..69a08822b06dc64 100644
--- a/libc/test/include/CMakeLists.txt
+++ b/libc/test/include/CMakeLists.txt
@@ -14,3 +14,22 @@ add_libc_test(
     # This is needed because the __containerof macro uses statement expression.
     -Wno-gnu-statement-expression-from-macro-expansion
 )
+
+add_libc_test(
+  stdbit_test
+  SUITE
+    libc_include_tests
+  SRCS
+    stdbit_test.cpp
+  DEPENDS
+    libc.__support.CPP.limits
+    libc.include.llvm-libc-macros.stdbit_macros
+    libc.src.stdbit.stdc_leading_zeros_uc
+    libc.src.stdbit.stdc_leading_zeros_ui
+    libc.src.stdbit.stdc_leading_zeros_ul
+    libc.src.stdbit.stdc_leading_zeros_ull
+    libc.src.stdbit.stdc_leading_zeros_us
+  COMPILE_OPTIONS
+    # stdbit is full of type generic macros implemented via C11 _Generic.
+    -Wno-c11-extensions
+)
diff --git a/libc/test/include/stdbit_test.cpp b/libc/test/include/stdbit_test.cpp
new file mode 100644
index 000000000000000..c2e019d1096ea16
--- /dev/null
+++ b/libc/test/include/stdbit_test.cpp
@@ -0,0 +1,22 @@
+//===-- Unittests for stdbit ----------------------------------------------===//
+//
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDSList-License-Identifier: Apache-2.0 WITH LLVM-exception
+//
+//===----------------------------------------------------------------------===//
+
+#include "test/UnitTest/Test.h"
+
+#include "llvm-libc-macros/stdbit-macros.h"
+#include "src/__support/CPP/limits.h" // UINT_WIDTH
+#include "src/stdbit/stdc_leading_zeros_uc.h"
+#include "src/stdbit/stdc_leading_zeros_ui.h"
+#include "src/stdbit/stdc_leading_zeros_ul.h"
+#include "src/stdbit/stdc_leading_zeros_ull.h"
+#include "src/stdbit/stdc_leading_zeros_us.h"
+
+TEST(LlvmLibcStdbitTest, TypeGenericMacro) {
+  using namespace LIBC_NAMESPACE;
+  EXPECT_EQ(stdc_leading_zeros(0U), static_cast<unsigned>(UINT_WIDTH));
+}
diff --git a/libc/test/src/CMakeLists.txt b/libc/test/src/CMakeLists.txt
index 6bd8ace9ea71af0..1f899c729e0abca 100644
--- a/libc/test/src/CMakeLists.txt
+++ b/libc/test/src/CMakeLists.txt
@@ -40,13 +40,14 @@ add_subdirectory(__support)
 add_subdirectory(ctype)
 add_subdirectory(errno)
 add_subdirectory(fenv)
-add_subdirectory(math)
-add_subdirectory(string)
-add_subdirectory(stdlib)
 add_subdirectory(inttypes)
+add_subdirectory(math)
+add_subdirectory(search)
+add_subdirectory(stdbit)
 add_subdirectory(stdio)
+add_subdirectory(stdlib)
+add_subdirectory(string)
 add_subdirectory(wchar)
-add_subdirectory(search)
 
 if(${LIBC_TARGET_OS} STREQUAL "linux")
   add_subdirectory(fcntl)
@@ -113,7 +114,7 @@ add_custom_target(libc-api-test)
 add_dependencies(check-libc libc-api-test)
 
 set(
-  allocator_entrypoints 
+  allocator_entrypoints
     libc.src.stdlib.malloc
     libc.src.stdlib.calloc
     libc.src.stdlib.realloc
diff --git a/libc/test/src/stdbit/CMakeLists.txt b/libc/test/src/stdbit/CMakeLists.txt
new file mode 100644
index 000000000000000..73b32e4ec0caeab
--- /dev/null
+++ b/libc/test/src/stdbit/CMakeLists.txt
@@ -0,0 +1,51 @@
+add_custom_target(libc-stdbit-tests)
+
+add_libc_test(
+  stdc_leading_zeros_uc_test
+  SUITE
+    libc-stdbit-tests
+  SRCS
+    stdc_leading_zeros_uc_test.cpp
+  DEPENDS
+    libc.src.stdbit.stdc_leading_zeros_uc
+)
+
+add_libc_test(
+  stdc_leading_zeros_us_test
+  SUITE
+    libc-stdbit-tests
+  SRCS
+    stdc_leading_zeros_us_test.cpp
+  DEPENDS
+    libc.src.stdbit.stdc_leading_zeros_us
+)
+
+add_libc_test(
+  stdc_leading_zeros_ui_test
+  SUITE
+    libc-stdbit-tests
+  SRCS
+    stdc_leading_zeros_ui_test.cpp
+  DEPENDS
+    libc.src.stdbit.stdc_leading_zeros_ui
+)
+
+add_libc_test(
+  stdc_leading_zeros_ul_test
+  SUITE
+    libc-stdbit-tests
+  SRCS
+    stdc_leading_zeros_ul_test.cpp
+  DEPENDS
+    libc.src.stdbit.stdc_leading_zeros_ul
+)
+
+add_libc_test(
+  stdc_leading_zeros_ull_test
+  SUITE
+    libc-stdbit-tests
+  SRCS
+    stdc_leading_zeros_ull_test.cpp
+  DEPENDS
+    libc.src.stdbit.stdc_leading_zeros_ull
+...
[truncated]

Copy link

github-actions bot commented Jan 27, 2024

✅ With the latest revision this PR passed the C/C++ code formatter.

libc.src.stdbit.stdc_leading_zeros_ull
libc.src.stdbit.stdc_leading_zeros_us
COMPILE_OPTIONS
# stdbit is full of type generic macros implemented via C11 _Generic.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

if you are using C11 features then why is the flag -Wno-c11-extensions? This comment may need some more detail.

Copy link
Member Author

@nickdesaulniers nickdesaulniers Jan 29, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

added more info in dfbf115e640e, but let me know if there's a better way to word this.

#include "src/stdbit/stdc_leading_zeros_us.h"

TEST(LlvmLibcStdbitTest, TypeGenericMacro) {
using namespace LIBC_NAMESPACE;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

generally in tests we should avoid doing using namespace LIBC_NAMESPACE since it means that if the namespaced symbol isn't available but the system one is, the test will still pass.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've changed this test significantly in 3386377, PTAL

#include "src/stdbit/stdc_leading_zeros_uc.h"
#include "test/UnitTest/Test.h"

#define LZ(x) LIBC_NAMESPACE::stdc_leading_zeros_uc((x))
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

given that this macro is used in two places, I think it's cleaner to not use the macro and instead write out the function call. Same for the other test files.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

done in 48efd94

@@ -0,0 +1,25 @@
//===-- Unittests for stdc_leading_zeros_ull
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nit: formatting

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

done in e7f6956

@SchrodingerZhu
Copy link
Contributor

https://snapshots.sourceware.org/glibc/trunk/latest/manual/html_node/Bit-Manipulation.html
Maybe not in this commit. Consider define the macros:

Macro: __STDC_ENDIAN_LITTLE__
This macro represents little-endian storage.

Macro: __STDC_ENDIAN_BIG__
This macro represents big-endian storage.

Macro: __STDC_ENDIAN_NATIVE__
This macro equals __STDC_ENDIAN_LITTLE__ if integer types are stored in memory in little-endian format, and equals __STDC_ENDIAN_BIG__ if integer types are stored in memory in big-endian format.

stdc_leading_zeros_uc.cpp
HDRS
stdc_leading_zeros_uc.h
)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can you add DEPENDS libc.src.__support.CPP.bit to these entrypoints?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

fixed in 7a898f3, good catch (I'll get the hang of this)

SRCS
stdc_leading_zeros_ull_test.cpp
DEPENDS
libc.src.stdbit.stdc_leading_zeros_ull
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can you add libc.src.__support.CPP.limits to their lists of dependency?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've removed this dependency in 3386377, but please triple check.

@lntue lntue requested a review from gchatelet January 29, 2024 14:14
Copy link
Contributor

@gchatelet gchatelet left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM, make sure to address Michael and Tue's comments.

@nickdesaulniers
Copy link
Member Author

https://snapshots.sourceware.org/glibc/trunk/latest/manual/html_node/Bit-Manipulation.html Maybe not in this commit. Consider define the macros:

Right, there's something like 70 functions to implement for stdbit.h. This PR is just 5 of them (with the corresponding type-generic macro). In terms of completeness, we'll need to ensure that we provide all of the preprocessor defines that the standard mandates. Since those macros may be used as feature detection, we should wait to provide them until the implementation is complete and tested.

Copy link
Contributor

@michaelrj-google michaelrj-google left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM

@nickdesaulniers nickdesaulniers merged commit 7bc5eaa into llvm:main Jan 29, 2024
@nickdesaulniers nickdesaulniers deleted the stdbit branch January 30, 2024 17:21
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

Successfully merging this pull request may close these issues.

6 participants