[libc-commits] [libc] [libc] Allow RPC interface to be compiled with MSVC (PR #190483)

Joseph Huber via libc-commits libc-commits at lists.llvm.org
Sat Apr 4 15:02:45 PDT 2026


https://github.com/jhuber6 updated https://github.com/llvm/llvm-project/pull/190483

>From 18f765ef58d771bbfffb3354ccd806e9e6450d89 Mon Sep 17 00:00:00 2001
From: Joseph Huber <huberjn at outlook.com>
Date: Sat, 4 Apr 2026 14:54:54 -0500
Subject: [PATCH] [libc] Allow RPC interface to be compiled with MSVC

Summary:
This should be portable to other compilers so it can support Windows
infrastructure.

I don't really use MSVC but godbolt seems happy: https://godbolt.org/z/Ysdx1Y1rq
---
 libc/shared/rpc.h      | 26 ++++++++++++++++++++++++--
 libc/shared/rpc_util.h |  5 +++++
 2 files changed, 29 insertions(+), 2 deletions(-)

diff --git a/libc/shared/rpc.h b/libc/shared/rpc.h
index 9886c3851b259..a27b0676e5957 100644
--- a/libc/shared/rpc.h
+++ b/libc/shared/rpc.h
@@ -20,10 +20,25 @@
 
 #include "rpc_util.h"
 
-namespace rpc {
-
 /// Use scoped atomic variants if they are available for the target.
 #if !__has_builtin(__scoped_atomic_load_n)
+#ifdef _MSC_VER // MSVC atomic support.
+#include <intrin.h>
+#define __scoped_atomic_load_n(src, ord, scp)                                  \
+  (decltype(*(src)))__iso_volatile_load32((const volatile int32_t *)(src))
+#define __scoped_atomic_store_n(dst, src, ord, scp)                            \
+  (sizeof(*(dst)) == 4                                                         \
+       ? __iso_volatile_store32((volatile int32_t *)(dst), (__int32)(src))     \
+       : __iso_volatile_store64((volatile int64_t *)(dst), (__int64)(src)))
+#define __scoped_atomic_fetch_or(src, val, ord, scp)                           \
+  _InterlockedOr((volatile long *)(src), (long)(val))
+#define __scoped_atomic_fetch_and(src, val, ord, scp)                          \
+  _InterlockedAnd((volatile long *)(src), (long)(val))
+#define __scoped_atomic_fetch_add(src, val, ord, scp)                          \
+  _InterlockedExchangeAdd64((volatile long long *)(src), (long long)(val))
+#define __scoped_atomic_fetch_sub(src, val, ord, scp)                          \
+  _InterlockedExchangeAdd64((volatile long long *)(src), -(long long)(val))
+#else // GNU atomic support.
 #define __scoped_atomic_load_n(src, ord, scp) __atomic_load_n(src, ord)
 #define __scoped_atomic_store_n(dst, src, ord, scp)                            \
   __atomic_store_n(dst, src, ord)
@@ -36,9 +51,16 @@ namespace rpc {
 #define __scoped_atomic_fetch_sub(src, val, ord, scp)                          \
   __atomic_fetch_sub(src, val, ord)
 #endif
+#endif
 #if !__has_builtin(__scoped_atomic_thread_fence)
+#ifdef _MSC_VER
+#define __scoped_atomic_thread_fence(ord, scp) _ReadWriteBarrier()
+#else
 #define __scoped_atomic_thread_fence(ord, scp) __atomic_thread_fence(ord)
 #endif
+#endif
+
+namespace rpc {
 
 /// Generic codes that can be used when implementing the server.
 enum RPCStatus {
diff --git a/libc/shared/rpc_util.h b/libc/shared/rpc_util.h
index c003db828fd74..09a97c63b562f 100644
--- a/libc/shared/rpc_util.h
+++ b/libc/shared/rpc_util.h
@@ -453,8 +453,13 @@ template <typename T, typename U> RPC_ATTRS T *advance(T *ptr, U bytes) {
 
 /// Wrapper around the optimal memory copy implementation for the target.
 RPC_ATTRS void rpc_memcpy(void *dst, const void *src, uint64_t count) {
+#if __has_builtin(__builtin_memcpy)
   if (count)
     __builtin_memcpy(dst, src, count);
+#else
+  for (uint64_t i = 0; i < count; ++i)
+    static_cast<uint8_t *>(dst)[i] = static_cast<const uint8_t *>(src)[i];
+#endif
 }
 
 /// Minimal string length function.



More information about the libc-commits mailing list