[libc-commits] [libc] [libc] Support configurable errno modes (PR #98287)
Petr Hosek via libc-commits
libc-commits at lists.llvm.org
Thu Jul 11 00:53:27 PDT 2024
================
@@ -9,44 +9,85 @@
#include "libc_errno.h"
#include "src/__support/CPP/atomic.h"
-#ifdef LIBC_TARGET_ARCH_IS_GPU
-// LIBC_THREAD_LOCAL on GPU currently does nothing. So essentially this is just
-// a global errno for gpu to use for now.
+#define LIBC_ERRNO_MODE_UNDEFINED 1
+#define LIBC_ERRNO_MODE_THREAD_LOCAL 2
+#define LIBC_ERRNO_MODE_SHARED 3
+#define LIBC_ERRNO_MODE_EXTERNAL 4
+#define LIBC_ERRNO_MODE_SYSTEM 5
+
+#ifndef LIBC_ERRNO_MODE
+#if defined(LIBC_FULL_BUILD) || !defined(LIBC_COPT_PUBLIC_PACKAGING)
+#define LIBC_ERRNO_MODE LIBC_ERRNO_MODE_THREAD_LOCAL
+#else
+#define LIBC_ERRNO_MODE LIBC_ERRNO_MODE_SYSTEM
+#endif
+#endif // LIBC_ERRNO_MODE
+
+#if LIBC_ERRNO_MODE != LIBC_ERRNO_MODE_UNDEFINED && \
+ LIBC_ERRNO_MODE != LIBC_ERRNO_MODE_THREAD_LOCAL && \
+ LIBC_ERRNO_MODE != LIBC_ERRNO_MODE_SHARED && \
+ LIBC_ERRNO_MODE != LIBC_ERRNO_MODE_EXTERNAL && \
+ LIBC_ERRNO_MODE != LIBC_ERRNO_MODE_SYSTEM
+#error LIBC_ERRNO_MODE must be one of the following values: \
+LIBC_ERRNO_MODE_UNDEFINED, \
+LIBC_ERRNO_MODE_THREAD_LOCAL, \
+LIBC_ERRNO_MODE_SHARED, \
+LIBC_ERRNO_MODE_EXTERNAL, \
+LIBC_ERRNO_MODE_SYSTEM
+#endif
+
+namespace LIBC_NAMESPACE {
+
+// Define the global `libc_errno` instance.
+Errno libc_errno;
+
+#if LIBC_ERRNO_MODE == LIBC_ERRNO_MODE_UNDEFINED
+
+void Errno::operator=(int) {}
+Errno::operator int() { return 0; }
+
+#elif LIBC_ERRNO_MODE == LIBC_ERRNO_MODE_THREAD_LOCAL
+
+namespace {
+LIBC_THREAD_LOCAL int thread_errno;
+}
+
extern "C" {
-LIBC_THREAD_LOCAL LIBC_NAMESPACE::cpp::Atomic<int> __llvmlibc_errno;
+int *__llvm_libc_errno() { return &thread_errno; }
}
-void LIBC_NAMESPACE::Errno::operator=(int a) {
- __llvmlibc_errno.store(a, cpp::MemoryOrder::RELAXED);
+void Errno::operator=(int a) { __libc_errno = a; }
+Errno::operator int() { return __libc_errno; }
+
+#elif LIBC_ERRNO_MODE == LIBC_ERRNO_MODE_GLOBAL
+
+namespace {
+cpp::Atomic<int> global_errno;
}
-LIBC_NAMESPACE::Errno::operator int() {
- return __llvmlibc_errno.load(cpp::MemoryOrder::RELAXED);
+
+extern "C" {
+int *__llvm_libc_errno() { return &global_errno; }
----------------
petrhosek wrote:
Yeah, I was just looking at that. `cpp::Atomic<T>` lets you [access the underlying value](https://github.com/llvm/llvm-project/blob/ce92b2f594809c39c37bf3ef3d881f2b33bd6730/libc/src/__support/CPP/atomic.h#L59) but accessing the value that way won't be atomic so I don't think this is really viable.
https://github.com/llvm/llvm-project/pull/98287
More information about the libc-commits
mailing list