From bda87e0a09d44cdc8cbd1f4209182c3ff94b3428 Mon Sep 17 00:00:00 2001 From: Krishna Pandey <47917477+krishna2803@users.noreply.github.com> Date: Wed, 19 Mar 2025 23:14:41 +0530 Subject: [PATCH] [libc][sched] Implement `CPU_ZERO`, `CPU_ISSET`, `CPU_SET` macros (#131524) This PR implements the following macros for `sched.h`: - `CPU_ZERO` - `CPU_ISSET` - `CPU_SET` Fixes #124642 --------- Signed-off-by: krishna2803 --- libc/config/linux/aarch64/entrypoints.txt | 3 ++ libc/config/linux/riscv/entrypoints.txt | 3 ++ libc/config/linux/x86_64/entrypoints.txt | 3 ++ libc/hdr/CMakeLists.txt | 9 ++++ libc/hdr/sched_macros.h | 22 +++++++++ libc/hdr/types/CMakeLists.txt | 8 ++++ libc/hdr/types/cpu_set_t.h | 22 +++++++++ .../llvm-libc-macros/linux/sched-macros.h | 8 ++++ libc/include/llvm-libc-types/cpu_set_t.h | 3 ++ libc/src/sched/CMakeLists.txt | 21 +++++++++ libc/src/sched/linux/CMakeLists.txt | 46 ++++++++++++++++++- libc/src/sched/linux/sched_getcpuisset.cpp | 36 +++++++++++++++ libc/src/sched/linux/sched_setcpuset.cpp | 33 +++++++++++++ libc/src/sched/linux/sched_setcpuzero.cpp | 26 +++++++++++ libc/src/sched/sched_getcpuisset.h | 24 ++++++++++ libc/src/sched/sched_setcpuset.h | 24 ++++++++++ libc/src/sched/sched_setcpuzero.h | 24 ++++++++++ 17 files changed, 314 insertions(+), 1 deletion(-) create mode 100644 libc/hdr/sched_macros.h create mode 100644 libc/hdr/types/cpu_set_t.h create mode 100644 libc/src/sched/linux/sched_getcpuisset.cpp create mode 100644 libc/src/sched/linux/sched_setcpuset.cpp create mode 100644 libc/src/sched/linux/sched_setcpuzero.cpp create mode 100644 libc/src/sched/sched_getcpuisset.h create mode 100644 libc/src/sched/sched_setcpuset.h create mode 100644 libc/src/sched/sched_setcpuzero.h diff --git a/libc/config/linux/aarch64/entrypoints.txt b/libc/config/linux/aarch64/entrypoints.txt index c1e688ea7e86..431975463fba 100644 --- a/libc/config/linux/aarch64/entrypoints.txt +++ b/libc/config/linux/aarch64/entrypoints.txt @@ -910,6 +910,9 @@ if(LLVM_LIBC_FULL_BUILD) # sched.h entrypoints libc.src.sched.__sched_getcpucount + libc.src.sched.__sched_setcpuzero + libc.src.sched.__sched_setcpuset + libc.src.sched.__sched_getcpuisset # strings.h entrypoints libc.src.strings.strcasecmp_l diff --git a/libc/config/linux/riscv/entrypoints.txt b/libc/config/linux/riscv/entrypoints.txt index ff238c3c32d9..c234ea256004 100644 --- a/libc/config/linux/riscv/entrypoints.txt +++ b/libc/config/linux/riscv/entrypoints.txt @@ -858,6 +858,9 @@ if(LLVM_LIBC_FULL_BUILD) # sched.h entrypoints libc.src.sched.__sched_getcpucount + libc.src.sched.__sched_setcpuzero + libc.src.sched.__sched_setcpuset + libc.src.sched.__sched_getcpuisset # setjmp.h entrypoints libc.src.setjmp.longjmp diff --git a/libc/config/linux/x86_64/entrypoints.txt b/libc/config/linux/x86_64/entrypoints.txt index 3cb9ee82752b..5abe6957d2e3 100644 --- a/libc/config/linux/x86_64/entrypoints.txt +++ b/libc/config/linux/x86_64/entrypoints.txt @@ -1028,6 +1028,9 @@ if(LLVM_LIBC_FULL_BUILD) # sched.h entrypoints libc.src.sched.__sched_getcpucount + libc.src.sched.__sched_setcpuzero + libc.src.sched.__sched_setcpuset + libc.src.sched.__sched_getcpuisset # setjmp.h entrypoints libc.src.setjmp.longjmp diff --git a/libc/hdr/CMakeLists.txt b/libc/hdr/CMakeLists.txt index b337a8c9fc2a..db2dac9ff282 100644 --- a/libc/hdr/CMakeLists.txt +++ b/libc/hdr/CMakeLists.txt @@ -72,6 +72,15 @@ add_proxy_header_library( libc.include.fenv ) +add_proxy_header_library( + sched_macros + HDRS + sched_macros.h + FULL_BUILD_DEPENDS + libc.include.sched + libc.include.llvm-libc-macros.sched_macros +) + add_proxy_header_library( signal_macros HDRS diff --git a/libc/hdr/sched_macros.h b/libc/hdr/sched_macros.h new file mode 100644 index 000000000000..cfeaa9979678 --- /dev/null +++ b/libc/hdr/sched_macros.h @@ -0,0 +1,22 @@ +//===-- Definition of macros from sched.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_HDR_SCHED_MACROS_H +#define LLVM_LIBC_HDR_SCHED_MACROS_H + +#ifdef LIBC_FULL_BUILD + +#include "include/llvm-libc-macros/sched-macros.h" + +#else // Overlay mode + +#include + +#endif // LLVM_LIBC_FULL_BUILD + +#endif // LLVM_LIBC_HDR_SCHED_MACROS_H diff --git a/libc/hdr/types/CMakeLists.txt b/libc/hdr/types/CMakeLists.txt index 5aa7b868c5e7..e43c6f455264 100644 --- a/libc/hdr/types/CMakeLists.txt +++ b/libc/hdr/types/CMakeLists.txt @@ -357,3 +357,11 @@ add_proxy_header_library( FULL_BUILD_DEPENDS libc.include.llvm-libc-types.struct_pollfd ) + +add_proxy_header_library( + cpu_set_t + HDRS + cpu_set_t.h + FULL_BUILD_DEPENDS + libc.include.llvm-libc-types.cpu_set_t +) diff --git a/libc/hdr/types/cpu_set_t.h b/libc/hdr/types/cpu_set_t.h new file mode 100644 index 000000000000..26aed7592fa2 --- /dev/null +++ b/libc/hdr/types/cpu_set_t.h @@ -0,0 +1,22 @@ +//===-- Proxy for cpu_set_t -----------------------------------------------===// +// +// 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_HDR_TYPES_CPU_SET_T_H +#define LLVM_LIBC_HDR_TYPES_CPU_SET_T_H + +#ifdef LIBC_FULL_BUILD + +#include "include/llvm-libc-types/cpu_set_t.h" + +#else // Overlay mode + +#include + +#endif // LLVM_LIBC_FULL_BUILD + +#endif // LLVM_LIBC_HDR_TYPES_CPU_SET_T_H diff --git a/libc/include/llvm-libc-macros/linux/sched-macros.h b/libc/include/llvm-libc-macros/linux/sched-macros.h index ace620049ca0..597789bb4ce2 100644 --- a/libc/include/llvm-libc-macros/linux/sched-macros.h +++ b/libc/include/llvm-libc-macros/linux/sched-macros.h @@ -23,7 +23,15 @@ #define SCHED_IDLE 5 #define SCHED_DEADLINE 6 +#define CPU_SETSIZE __CPU_SETSIZE +#define NCPUBITS __NCPUBITS #define CPU_COUNT_S(setsize, set) __sched_getcpucount(setsize, set) #define CPU_COUNT(set) CPU_COUNT_S(sizeof(cpu_set_t), set) +#define CPU_ZERO_S(setsize, set) __sched_setcpuzero(setsize, set) +#define CPU_ZERO(set) CPU_ZERO_S(sizeof(cpu_set_t), set) +#define CPU_SET_S(cpu, setsize, set) __sched_setcpuset(cpu, setsize, set) +#define CPU_SET(cpu, setsize, set) CPU_SET_S(cpu, sizeof(cpt_set_t), set) +#define CPU_ISSET_S(cpu, setsize, set) __sched_getcpuisset(cpu, setsize, set) +#define CPU_ISSET(cpu, setsize, set) CPU_ISSET_S(cpu, sizeof(cpt_set_t), set) #endif // LLVM_LIBC_MACROS_LINUX_SCHED_MACROS_H diff --git a/libc/include/llvm-libc-types/cpu_set_t.h b/libc/include/llvm-libc-types/cpu_set_t.h index e7f52597e147..8c6859de5f1d 100644 --- a/libc/include/llvm-libc-types/cpu_set_t.h +++ b/libc/include/llvm-libc-types/cpu_set_t.h @@ -9,6 +9,9 @@ #ifndef LLVM_LIBC_TYPES_CPU_SET_T_H #define LLVM_LIBC_TYPES_CPU_SET_T_H +#define __CPU_SETSIZE 1024 +#define __NCPUBITS (8 * sizeof(unsigned long)) + typedef struct { // If a processor with more than 1024 CPUs is to be supported in future, // we need to adjust the size of this array. diff --git a/libc/src/sched/CMakeLists.txt b/libc/src/sched/CMakeLists.txt index a98940c55abd..e6c37d3b0433 100644 --- a/libc/src/sched/CMakeLists.txt +++ b/libc/src/sched/CMakeLists.txt @@ -78,3 +78,24 @@ add_entrypoint_object( DEPENDS .${LIBC_TARGET_OS}.__sched_getcpucount ) + +add_entrypoint_object( + __sched_setcpuzero + ALIAS + DEPENDS + .${LIBC_TARGET_OS}.__sched_setcpuzero +) + +add_entrypoint_object( + __sched_setcpuset + ALIAS + DEPENDS + .${LIBC_TARGET_OS}.__sched_setcpuset +) + +add_entrypoint_object( + __sched_getcpuisset + ALIAS + DEPENDS + .${LIBC_TARGET_OS}.__sched_getcpuisset +) diff --git a/libc/src/sched/linux/CMakeLists.txt b/libc/src/sched/linux/CMakeLists.txt index ac95bf85da53..4852c9053bea 100644 --- a/libc/src/sched/linux/CMakeLists.txt +++ b/libc/src/sched/linux/CMakeLists.txt @@ -30,7 +30,7 @@ add_entrypoint_object( ../sched_getcpucount.h DEPENDS libc.include.sched - ) +) add_entrypoint_object( sched_yield @@ -135,3 +135,47 @@ add_entrypoint_object( libc.src.__support.OSUtil.osutil libc.src.errno.errno ) + +add_entrypoint_object( + __sched_setcpuzero + SRCS + sched_setcpuzero.cpp + HDRS + ../sched_setcpuzero.h + DEPENDS + libc.src.__support.common + libc.src.__support.macros.config + libc.src.__support.macros.null_check + libc.hdr.types.cpu_set_t + libc.hdr.types.size_t +) + +add_entrypoint_object( + __sched_setcpuset + SRCS + sched_setcpuset.cpp + HDRS + ../sched_setcpuset.h + DEPENDS + libc.src.__support.common + libc.src.__support.macros.config + libc.src.__support.macros.null_check + libc.hdr.sched_macros + libc.hdr.types.cpu_set_t + libc.hdr.types.size_t +) + +add_entrypoint_object( + __sched_getcpuisset + SRCS + sched_getcpuisset.cpp + HDRS + ../sched_getcpuisset.h + DEPENDS + libc.src.__support.common + libc.src.__support.macros.config + libc.src.__support.macros.null_check + libc.hdr.sched_macros + libc.hdr.types.cpu_set_t + libc.hdr.types.size_t +) diff --git a/libc/src/sched/linux/sched_getcpuisset.cpp b/libc/src/sched/linux/sched_getcpuisset.cpp new file mode 100644 index 000000000000..da9f97127d07 --- /dev/null +++ b/libc/src/sched/linux/sched_getcpuisset.cpp @@ -0,0 +1,36 @@ +//===-- Implementation of sched_getcpuisset -------------------------------===// +// +// 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/sched/sched_getcpuisset.h" + +#include "src/__support/common.h" // LLVM_LIBC_FUNCTION +#include "src/__support/macros/config.h" // LIBC_NAMESPACE_DECL +#include "src/__support/macros/null_check.h" // LIBC_CRASH_ON_NULLPTR + +#include "hdr/sched_macros.h" // NCPUBITS +#include "hdr/types/cpu_set_t.h" +#include "hdr/types/size_t.h" + +namespace LIBC_NAMESPACE_DECL { + +LLVM_LIBC_FUNCTION(int, __sched_getcpuisset, + (int cpu, const size_t cpuset_size, cpu_set_t *set)) { + LIBC_CRASH_ON_NULLPTR(set); + + if (static_cast(cpu) / 8 < cpuset_size) { + const size_t element_index = static_cast(cpu) / NCPUBITS; + const size_t bit_position = static_cast(cpu) % NCPUBITS; + + const unsigned long mask = 1UL << bit_position; + return (set->__mask[element_index] & mask) != 0; + } + + return 0; +} + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/sched/linux/sched_setcpuset.cpp b/libc/src/sched/linux/sched_setcpuset.cpp new file mode 100644 index 000000000000..88209d854ca8 --- /dev/null +++ b/libc/src/sched/linux/sched_setcpuset.cpp @@ -0,0 +1,33 @@ +//===-- Implementation of sched_setcpuset ---------------------------------===// +// +// 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/sched/sched_setcpuset.h" + +#include "src/__support/common.h" // LLVM_LIBC_FUNCTION +#include "src/__support/macros/config.h" // LIBC_NAMESPACE_DECL +#include "src/__support/macros/null_check.h" // LIBC_CRASH_ON_NULLPTR + +#include "hdr/sched_macros.h" // NCPUBITS +#include "hdr/types/cpu_set_t.h" +#include "hdr/types/size_t.h" + +namespace LIBC_NAMESPACE_DECL { + +LLVM_LIBC_FUNCTION(void, __sched_setcpuset, + (int cpu, const size_t cpuset_size, cpu_set_t *set)) { + LIBC_CRASH_ON_NULLPTR(set); + if (static_cast(cpu) / 8 < cpuset_size) { + const size_t element_index = static_cast(cpu) / NCPUBITS; + const size_t bit_position = static_cast(cpu) % NCPUBITS; + + const unsigned long mask = 1UL << bit_position; + set->__mask[element_index] |= mask; + } +} + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/sched/linux/sched_setcpuzero.cpp b/libc/src/sched/linux/sched_setcpuzero.cpp new file mode 100644 index 000000000000..28c789a7f25b --- /dev/null +++ b/libc/src/sched/linux/sched_setcpuzero.cpp @@ -0,0 +1,26 @@ +//===-- Implementation of sched_setcpuzero --------------------------------===// +// +// 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/sched/sched_setcpuzero.h" + +#include "src/__support/common.h" // LLVM_LIBC_FUNCTION +#include "src/__support/macros/config.h" // LIBC_NAMESPACE_DECL +#include "src/__support/macros/null_check.h" // LIBC_CRASH_ON_NULLPTR + +#include "hdr/types/cpu_set_t.h" +#include "hdr/types/size_t.h" + +namespace LIBC_NAMESPACE_DECL { + +LLVM_LIBC_FUNCTION(void, __sched_setcpuzero, + (const size_t cpuset_size, cpu_set_t *set)) { + LIBC_CRASH_ON_NULLPTR(set); + __builtin_memset(set, 0, cpuset_size); +} + +} // namespace LIBC_NAMESPACE_DECL diff --git a/libc/src/sched/sched_getcpuisset.h b/libc/src/sched/sched_getcpuisset.h new file mode 100644 index 000000000000..8e6f69c44313 --- /dev/null +++ b/libc/src/sched/sched_getcpuisset.h @@ -0,0 +1,24 @@ +//===-- Implementation header for sched_getcpuisset -------------*- 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_SCHED_SCHED_GETCPUISSET_H +#define LLVM_LIBC_SRC_SCHED_SCHED_GETCPUISSET_H + +#include "src/__support/macros/config.h" // LIBC_NAMESPACE_DECL + +#include "hdr/types/cpu_set_t.h" +#include "hdr/types/size_t.h" + +namespace LIBC_NAMESPACE_DECL { + +// for internal use in the CPU_ISSET macro +int __sched_getcpuisset(int cpu, const size_t cpuset_size, cpu_set_t *set); + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_SCHED_SCHED_GETCPUISSET_H diff --git a/libc/src/sched/sched_setcpuset.h b/libc/src/sched/sched_setcpuset.h new file mode 100644 index 000000000000..38d6cd29e61d --- /dev/null +++ b/libc/src/sched/sched_setcpuset.h @@ -0,0 +1,24 @@ +//===-- Implementation header for sched_setcpuset ---------------*- 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_SCHED_SCHED_SETCPUSET_H +#define LLVM_LIBC_SRC_SCHED_SCHED_SETCPUSET_H + +#include "src/__support/macros/config.h" + +#include "hdr/types/cpu_set_t.h" +#include "hdr/types/size_t.h" + +namespace LIBC_NAMESPACE_DECL { + +// for internal use in the CPU_SET macro +void __sched_setcpuset(int cpu, const size_t cpuset_size, cpu_set_t *set); + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_SCHED_SCHED_SETCPUSET_H diff --git a/libc/src/sched/sched_setcpuzero.h b/libc/src/sched/sched_setcpuzero.h new file mode 100644 index 000000000000..53a0b4569665 --- /dev/null +++ b/libc/src/sched/sched_setcpuzero.h @@ -0,0 +1,24 @@ +//===-- Implementation header for sched_setcpuzero --------------*- 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_SCHED_SCHED_SETCPUZERO_H +#define LLVM_LIBC_SRC_SCHED_SCHED_SETCPUZERO_H + +#include "src/__support/macros/config.h" + +#include "hdr/types/cpu_set_t.h" +#include "hdr/types/size_t.h" + +namespace LIBC_NAMESPACE_DECL { + +// for internal use in the CPU_ZERO macro +void __sched_setcpuzero(const size_t cpuset_size, cpu_set_t *set); + +} // namespace LIBC_NAMESPACE_DECL + +#endif // LLVM_LIBC_SRC_SCHED_SCHED_SETCPUZERO_H