[libcxx-commits] [clang] [libcxxabi] [llvm] Add support for WASI builds (PR #91051)

via libcxx-commits libcxx-commits at lists.llvm.org
Sat Jun 8 16:44:47 PDT 2024


llvmbot wrote:


<!--LLVM PR SUMMARY COMMENT-->

@llvm/pr-subscribers-clang-driver

Author: Luca Versari (veluca93)

<details>
<summary>Changes</summary>

This PR modifies the LLVM source code to compile (and run) in a WASI environment.

The question of whether having WASI support in LLVM is one that doesn't have a clear answer for me (although of course I can see some use cases), but since the patch ended up being small enough I figured I'd create a PR and see what the LLVM community would make of it :-)

The code compiles & runs successfully when compiled with an unmodified wasi-libc (I only tested running clang++ and wasm-ld).

Caveats:
- a bunch of things are not supported. Most importantly, executing binaries is not supported, but also memory mapping, signals, dynamic linking, set/longjump, and JIT.
- There are no tests. I also would not know how to go about adding tests.
- Some projects are disabled on WASI.

---

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


19 Files Affected:

- (modified) clang/CMakeLists.txt (+1-1) 
- (modified) clang/lib/Driver/Driver.cpp (+1-1) 
- (modified) libcxxabi/src/CMakeLists.txt (+2-2) 
- (modified) llvm/cmake/modules/HandleLLVMOptions.cmake (+4) 
- (modified) llvm/include/llvm/ADT/bit.h (+2-2) 
- (modified) llvm/include/llvm/Support/Memory.h (+2) 
- (modified) llvm/lib/CMakeLists.txt (+2) 
- (modified) llvm/lib/Support/CrashRecoveryContext.cpp (+30-18) 
- (modified) llvm/lib/Support/LockFileManager.cpp (+11-8) 
- (modified) llvm/lib/Support/Unix/Memory.inc (+20) 
- (modified) llvm/lib/Support/Unix/Path.inc (+41-3) 
- (modified) llvm/lib/Support/Unix/Process.inc (+14-1) 
- (modified) llvm/lib/Support/Unix/Program.inc (+16-1) 
- (modified) llvm/lib/Support/Unix/Signals.inc (+14) 
- (modified) llvm/lib/Support/Unix/Unix.h (+9-6) 
- (modified) llvm/lib/Support/Unix/Watchdog.inc (+2-2) 
- (modified) llvm/lib/Support/raw_socket_stream.cpp (+22-2) 
- (modified) llvm/lib/Transforms/CMakeLists.txt (+2) 
- (modified) llvm/tools/CMakeLists.txt (+4) 


``````````diff
diff --git a/clang/CMakeLists.txt b/clang/CMakeLists.txt
index 2ac0bccb42f50..e1da8297ddd5f 100644
--- a/clang/CMakeLists.txt
+++ b/clang/CMakeLists.txt
@@ -426,7 +426,7 @@ CMAKE_DEPENDENT_OPTION(CLANG_PLUGIN_SUPPORT
 # If libstdc++ is statically linked, clang-repl needs to statically link libstdc++
 # itself, which is not possible in many platforms because of current limitations in
 # JIT stack. (more platforms need to be supported by JITLink)
-if(NOT LLVM_STATIC_LINK_CXX_STDLIB)
+if(NOT LLVM_STATIC_LINK_CXX_STDLIB AND NOT WASI)
   set(HAVE_CLANG_REPL_SUPPORT ON)
 endif()
 
diff --git a/clang/lib/Driver/Driver.cpp b/clang/lib/Driver/Driver.cpp
index f5ea73a04ae5c..4f117a1d3a5ca 100644
--- a/clang/lib/Driver/Driver.cpp
+++ b/clang/lib/Driver/Driver.cpp
@@ -1577,7 +1577,7 @@ bool Driver::getCrashDiagnosticFile(StringRef ReproCrashFilename,
     CrashDiagDir = "/";
   path::append(CrashDiagDir, "Library/Logs/DiagnosticReports");
   int PID =
-#if LLVM_ON_UNIX
+#if LLVM_ON_UNIX && !defined(__wasi__)
       getpid();
 #else
       0;
diff --git a/libcxxabi/src/CMakeLists.txt b/libcxxabi/src/CMakeLists.txt
index c54ced4dc3ea8..f96d23b3c0315 100644
--- a/libcxxabi/src/CMakeLists.txt
+++ b/libcxxabi/src/CMakeLists.txt
@@ -36,8 +36,8 @@ else()
   )
 endif()
 
-if (LIBCXXABI_ENABLE_THREADS AND (UNIX OR FUCHSIA) AND NOT (APPLE OR CYGWIN)
-    AND NOT (${CMAKE_SYSTEM_NAME} MATCHES "AIX"))
+if (LIBCXXABI_ENABLE_THREADS AND (UNIX OR FUCHSIA OR WASI) AND NOT
+  (APPLE OR CYGWIN) AND NOT (${CMAKE_SYSTEM_NAME} MATCHES "AIX"))
   list(APPEND LIBCXXABI_SOURCES
     cxa_thread_atexit.cpp
   )
diff --git a/llvm/cmake/modules/HandleLLVMOptions.cmake b/llvm/cmake/modules/HandleLLVMOptions.cmake
index 5ca580fbb59c5..11cc1af78b9ba 100644
--- a/llvm/cmake/modules/HandleLLVMOptions.cmake
+++ b/llvm/cmake/modules/HandleLLVMOptions.cmake
@@ -217,6 +217,10 @@ elseif(FUCHSIA OR UNIX)
   else()
     set(LLVM_HAVE_LINK_VERSION_SCRIPT 1)
   endif()
+elseif(WASI)
+  set(LLVM_ON_WIN32 0)
+  set(LLVM_ON_UNIX 1)
+  set(LLVM_HAVE_LINK_VERSION_SCRIPT 0)
 elseif(CMAKE_SYSTEM_NAME STREQUAL "Generic")
   set(LLVM_ON_WIN32 0)
   set(LLVM_ON_UNIX 0)
diff --git a/llvm/include/llvm/ADT/bit.h b/llvm/include/llvm/ADT/bit.h
index c42b5e686bdc9..8dcf6a8bfbb0a 100644
--- a/llvm/include/llvm/ADT/bit.h
+++ b/llvm/include/llvm/ADT/bit.h
@@ -24,12 +24,12 @@
 #endif
 
 #if defined(_MSC_VER) && !defined(_DEBUG)
-#include <cstdlib>  // for _byteswap_{ushort,ulong,uint64}
+#include <cstdlib> // for _byteswap_{ushort,ulong,uint64}
 #endif
 
 #if defined(__linux__) || defined(__GNU__) || defined(__HAIKU__) ||            \
     defined(__Fuchsia__) || defined(__EMSCRIPTEN__) || defined(__NetBSD__) ||  \
-    defined(__OpenBSD__) || defined(__DragonFly__)
+    defined(__OpenBSD__) || defined(__DragonFly__) || defined(__wasi__)
 #include <endian.h>
 #elif defined(_AIX)
 #include <sys/machine.h>
diff --git a/llvm/include/llvm/Support/Memory.h b/llvm/include/llvm/Support/Memory.h
index d7d60371d315f..2d61f6da225b6 100644
--- a/llvm/include/llvm/Support/Memory.h
+++ b/llvm/include/llvm/Support/Memory.h
@@ -41,7 +41,9 @@ namespace sys {
   private:
     void *Address;    ///< Address of first byte of memory area
     size_t AllocatedSize; ///< Size, in bytes of the memory area
+#ifndef __wasi__
     unsigned Flags = 0;
+#endif
     friend class Memory;
   };
 
diff --git a/llvm/lib/CMakeLists.txt b/llvm/lib/CMakeLists.txt
index 74e2d03c07953..b32411ae0b860 100644
--- a/llvm/lib/CMakeLists.txt
+++ b/llvm/lib/CMakeLists.txt
@@ -31,7 +31,9 @@ add_subdirectory(Remarks)
 add_subdirectory(Debuginfod)
 add_subdirectory(DebugInfo)
 add_subdirectory(DWP)
+if (NOT WASI)
 add_subdirectory(ExecutionEngine)
+endif ()
 add_subdirectory(Target)
 add_subdirectory(AsmParser)
 add_subdirectory(LineEditor)
diff --git a/llvm/lib/Support/CrashRecoveryContext.cpp b/llvm/lib/Support/CrashRecoveryContext.cpp
index f53aea177d612..858ec64b7d53c 100644
--- a/llvm/lib/Support/CrashRecoveryContext.cpp
+++ b/llvm/lib/Support/CrashRecoveryContext.cpp
@@ -7,6 +7,7 @@
 //===----------------------------------------------------------------------===//
 
 #include "llvm/Support/CrashRecoveryContext.h"
+
 #include "llvm/Config/llvm-config.h"
 #include "llvm/Support/ErrorHandling.h"
 #include "llvm/Support/ExitCodes.h"
@@ -14,7 +15,9 @@
 #include "llvm/Support/thread.h"
 #include <cassert>
 #include <mutex>
+#ifndef __wasi__
 #include <setjmp.h>
+#endif
 
 using namespace llvm;
 
@@ -31,7 +34,9 @@ struct CrashRecoveryContextImpl {
   const CrashRecoveryContextImpl *Next;
 
   CrashRecoveryContext *CRC;
+#ifndef __wasi__
   ::jmp_buf JumpBuffer;
+#endif
   volatile unsigned Failed : 1;
   unsigned SwitchedThread : 1;
   unsigned ValidJumpBuffer : 1;
@@ -72,9 +77,11 @@ struct CrashRecoveryContextImpl {
 
     CRC->RetCode = RetCode;
 
+#ifndef __wasi__
     // Jump back to the RunSafely we were called under.
     if (ValidJumpBuffer)
       longjmp(JumpBuffer, 1);
+#endif
 
     // Otherwise let the caller decide of the outcome of the crash. Currently
     // this occurs when using SEH on Windows with MSVC or clang-cl.
@@ -118,7 +125,7 @@ CrashRecoveryContext::~CrashRecoveryContext() {
   }
   IsRecoveringFromCrash = PC;
 
-  CrashRecoveryContextImpl *CRCI = (CrashRecoveryContextImpl *) Impl;
+  CrashRecoveryContextImpl *CRCI = (CrashRecoveryContextImpl *)Impl;
   delete CRCI;
 }
 
@@ -154,8 +161,8 @@ void CrashRecoveryContext::Disable() {
   uninstallExceptionOrSignalHandlers();
 }
 
-void CrashRecoveryContext::registerCleanup(CrashRecoveryContextCleanup *cleanup)
-{
+void CrashRecoveryContext::registerCleanup(
+    CrashRecoveryContextCleanup *cleanup) {
   if (!cleanup)
     return;
   if (head)
@@ -164,16 +171,15 @@ void CrashRecoveryContext::registerCleanup(CrashRecoveryContextCleanup *cleanup)
   head = cleanup;
 }
 
-void
-CrashRecoveryContext::unregisterCleanup(CrashRecoveryContextCleanup *cleanup) {
+void CrashRecoveryContext::unregisterCleanup(
+    CrashRecoveryContextCleanup *cleanup) {
   if (!cleanup)
     return;
   if (cleanup == head) {
     head = cleanup->next;
     if (head)
       head->prev = nullptr;
-  }
-  else {
+  } else {
     cleanup->prev->next = cleanup->next;
     if (cleanup->next)
       cleanup->next->prev = cleanup->prev;
@@ -263,16 +269,14 @@ bool CrashRecoveryContext::RunSafely(function_ref<void()> Fn) {
 
 #include "llvm/Support/Windows/WindowsSupport.h"
 
-static LONG CALLBACK ExceptionHandler(PEXCEPTION_POINTERS ExceptionInfo)
-{
+static LONG CALLBACK ExceptionHandler(PEXCEPTION_POINTERS ExceptionInfo) {
   // DBG_PRINTEXCEPTION_WIDE_C is not properly defined on all supported
   // compilers and platforms, so we define it manually.
   constexpr ULONG DbgPrintExceptionWideC = 0x4001000AL;
-  switch (ExceptionInfo->ExceptionRecord->ExceptionCode)
-  {
+  switch (ExceptionInfo->ExceptionRecord->ExceptionCode) {
   case DBG_PRINTEXCEPTION_C:
   case DbgPrintExceptionWideC:
-  case 0x406D1388:  // set debugger thread name
+  case 0x406D1388: // set debugger thread name
     return EXCEPTION_CONTINUE_EXECUTION;
   }
 
@@ -307,7 +311,7 @@ static LONG CALLBACK ExceptionHandler(PEXCEPTION_POINTERS ExceptionInfo)
 // CrashRecoveryContext at all.  So we make use of a thread-local
 // exception table.  The handles contained in here will either be
 // non-NULL, valid VEH handles, or NULL.
-static LLVM_THREAD_LOCAL const void* sCurrentExceptionHandle;
+static LLVM_THREAD_LOCAL const void *sCurrentExceptionHandle;
 
 static void installExceptionOrSignalHandlers() {
   // We can set up vectored exception handling now.  We will install our
@@ -342,10 +346,11 @@ static void uninstallExceptionOrSignalHandlers() {
 // reliable fashion -- if we get a signal outside of a crash recovery context we
 // simply disable crash recovery and raise the signal again.
 
+#ifndef __wasi__
 #include <signal.h>
 
-static const int Signals[] =
-    { SIGABRT, SIGBUS, SIGFPE, SIGILL, SIGSEGV, SIGTRAP };
+static const int Signals[] = {SIGABRT, SIGBUS,  SIGFPE,
+                              SIGILL,  SIGSEGV, SIGTRAP};
 static const unsigned NumSignals = std::size(Signals);
 static struct sigaction PrevActions[NumSignals];
 
@@ -389,8 +394,10 @@ static void CrashRecoverySignalHandler(int Signal) {
   if (CRCI)
     const_cast<CrashRecoveryContextImpl *>(CRCI)->HandleCrash(RetCode, Signal);
 }
+#endif
 
 static void installExceptionOrSignalHandlers() {
+#ifndef __wasi__
   // Setup the signal handler.
   struct sigaction Handler;
   Handler.sa_handler = CrashRecoverySignalHandler;
@@ -400,12 +407,15 @@ static void installExceptionOrSignalHandlers() {
   for (unsigned i = 0; i != NumSignals; ++i) {
     sigaction(Signals[i], &Handler, &PrevActions[i]);
   }
+#endif
 }
 
 static void uninstallExceptionOrSignalHandlers() {
+#ifndef __wasi__
   // Restore the previous signal handlers.
   for (unsigned i = 0; i != NumSignals; ++i)
     sigaction(Signals[i], &PrevActions[i], nullptr);
+#endif
 }
 
 #endif // !_WIN32
@@ -418,9 +428,11 @@ bool CrashRecoveryContext::RunSafely(function_ref<void()> Fn) {
     Impl = CRCI;
 
     CRCI->ValidJumpBuffer = true;
+#ifndef __wasi__
     if (setjmp(CRCI->JumpBuffer) != 0) {
       return false;
     }
+#endif
   }
 
   Fn();
@@ -469,7 +481,7 @@ bool CrashRecoveryContext::throwIfCrash(int RetCode) {
     return false;
 #if defined(_WIN32)
   ::RaiseException(RetCode, 0, 0, NULL);
-#else
+#elif !defined(__wasi__)
   llvm::sys::unregisterHandlers();
   raise(RetCode - 128);
 #endif
@@ -502,7 +514,7 @@ struct RunSafelyOnThreadInfo {
 
 static void RunSafelyOnThread_Dispatch(void *UserData) {
   RunSafelyOnThreadInfo *Info =
-    reinterpret_cast<RunSafelyOnThreadInfo*>(UserData);
+      reinterpret_cast<RunSafelyOnThreadInfo *>(UserData);
 
   if (Info->UseBackgroundPriority)
     setThreadBackgroundPriority();
@@ -512,7 +524,7 @@ static void RunSafelyOnThread_Dispatch(void *UserData) {
 bool CrashRecoveryContext::RunSafelyOnThread(function_ref<void()> Fn,
                                              unsigned RequestedStackSize) {
   bool UseBackgroundPriority = hasThreadBackgroundPriority();
-  RunSafelyOnThreadInfo Info = { Fn, this, UseBackgroundPriority, false };
+  RunSafelyOnThreadInfo Info = {Fn, this, UseBackgroundPriority, false};
   llvm::thread Thread(RequestedStackSize == 0
                           ? std::nullopt
                           : std::optional<unsigned>(RequestedStackSize),
diff --git a/llvm/lib/Support/LockFileManager.cpp b/llvm/lib/Support/LockFileManager.cpp
index 3169aa25ec0d9..06b778a1d9dc7 100644
--- a/llvm/lib/Support/LockFileManager.cpp
+++ b/llvm/lib/Support/LockFileManager.cpp
@@ -34,7 +34,9 @@
 #include <unistd.h>
 #endif
 
-#if defined(__APPLE__) && defined(__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__) && (__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__ > 1050)
+#if defined(__APPLE__) &&                                                      \
+    defined(__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__) &&                  \
+    (__ENVIRONMENT_MAC_OS_X_VERSION_MIN_REQUIRED__ > 1050)
 #define USE_OSX_GETHOSTUUID 1
 #else
 #define USE_OSX_GETHOSTUUID 0
@@ -94,7 +96,7 @@ static std::error_code getHostID(SmallVectorImpl<char> &HostID) {
   StringRef UUIDRef(UUIDStr);
   HostID.append(UUIDRef.begin(), UUIDRef.end());
 
-#elif LLVM_ON_UNIX
+#elif LLVM_ON_UNIX && !defined(__wasi__)
   char HostName[256];
   HostName[255] = 0;
   HostName[0] = 0;
@@ -116,9 +118,11 @@ bool LockFileManager::processStillExecuting(StringRef HostID, int PID) {
   if (getHostID(StoredHostID))
     return true; // Conservatively assume it's executing on error.
 
-  // Check whether the process is dead. If so, we're done.
+    // Check whether the process is dead. If so, we're done.
+#ifndef __wasi__ // no other processes anyway
   if (StoredHostID == HostID && getsid(PID) == -1 && errno == ESRCH)
     return false;
+#endif
 #endif
 
   return true;
@@ -136,9 +140,10 @@ namespace {
 class RemoveUniqueLockFileOnSignal {
   StringRef Filename;
   bool RemoveImmediately;
+
 public:
   RemoveUniqueLockFileOnSignal(StringRef Name)
-  : Filename(Name), RemoveImmediately(true) {
+      : Filename(Name), RemoveImmediately(true) {
     sys::RemoveFileOnSignal(Filename, nullptr);
   }
 
@@ -157,8 +162,7 @@ class RemoveUniqueLockFileOnSignal {
 
 } // end anonymous namespace
 
-LockFileManager::LockFileManager(StringRef FileName)
-{
+LockFileManager::LockFileManager(StringRef FileName) {
   this->FileName = FileName;
   if (std::error_code EC = sys::fs::make_absolute(this->FileName)) {
     std::string S("failed to obtain absolute path for ");
@@ -217,8 +221,7 @@ LockFileManager::LockFileManager(StringRef FileName)
 
   while (true) {
     // Create a link from the lock file name. If this succeeds, we're done.
-    std::error_code EC =
-        sys::fs::create_link(UniqueLockFileName, LockFileName);
+    std::error_code EC = sys::fs::create_link(UniqueLockFileName, LockFileName);
     if (!EC) {
       RemoveUniqueFile.lockAcquired();
       return;
diff --git a/llvm/lib/Support/Unix/Memory.inc b/llvm/lib/Support/Unix/Memory.inc
index bac208a7d543c..4172886e66f82 100644
--- a/llvm/lib/Support/Unix/Memory.inc
+++ b/llvm/lib/Support/Unix/Memory.inc
@@ -36,6 +36,7 @@ extern "C" void sys_icache_invalidate(const void *Addr, size_t len);
 extern "C" void __clear_cache(void *, void *);
 #endif
 
+#ifndef __wasi__
 static int getPosixProtectionFlags(unsigned Flags) {
   switch (Flags & llvm::sys::Memory::MF_RWE_MASK) {
   case llvm::sys::Memory::MF_READ:
@@ -66,6 +67,7 @@ static int getPosixProtectionFlags(unsigned Flags) {
   // Provide a default return value as required by some compilers.
   return PROT_NONE;
 }
+#endif
 
 namespace llvm {
 namespace sys {
@@ -77,6 +79,17 @@ MemoryBlock Memory::allocateMappedMemory(size_t NumBytes,
   if (NumBytes == 0)
     return MemoryBlock();
 
+#ifdef __wasi__
+  MemoryBlock Result;
+  Result.Address = malloc(NumBytes);
+  if (!Result.Address) {
+    EC = errnoAsErrorCode();
+    Result.AllocatedSize = 0;
+  } else {
+    Result.AllocatedSize = NumBytes;
+  }
+  return Result;
+#else
   // On platforms that have it, we can use MAP_ANON to get a memory-mapped
   // page without file backing, but we need a fallback of opening /dev/zero
   // for strictly POSIX platforms instead.
@@ -146,14 +159,19 @@ MemoryBlock Memory::allocateMappedMemory(size_t NumBytes,
   }
 
   return Result;
+#endif
 }
 
 std::error_code Memory::releaseMappedMemory(MemoryBlock &M) {
+#ifdef __wasi__
+  free(M.Address);
+#else
   if (M.Address == nullptr || M.AllocatedSize == 0)
     return std::error_code();
 
   if (0 != ::munmap(M.Address, M.AllocatedSize))
     return errnoAsErrorCode();
+#endif
 
   M.Address = nullptr;
   M.AllocatedSize = 0;
@@ -163,6 +181,7 @@ std::error_code Memory::releaseMappedMemory(MemoryBlock &M) {
 
 std::error_code Memory::protectMappedMemory(const MemoryBlock &M,
                                             unsigned Flags) {
+#ifndef __wasi__
   static const Align PageSize = Align(Process::getPageSizeEstimate());
   if (M.Address == nullptr || M.AllocatedSize == 0)
     return std::error_code();
@@ -200,6 +219,7 @@ std::error_code Memory::protectMappedMemory(const MemoryBlock &M,
 
   if (InvalidateCache)
     Memory::InvalidateInstructionCache(M.Address, M.AllocatedSize);
+#endif
 
   return std::error_code();
 }
diff --git a/llvm/lib/Support/Unix/Path.inc b/llvm/lib/Support/Unix/Path.inc
index 6e679f74869f0..32d4b9e66682f 100644
--- a/llvm/lib/Support/Unix/Path.inc
+++ b/llvm/lib/Support/Unix/Path.inc
@@ -32,7 +32,9 @@
 #endif
 
 #include <dirent.h>
+#ifndef __wasi__
 #include <pwd.h>
+#endif
 #include <sys/file.h>
 
 #ifdef __APPLE__
@@ -191,7 +193,9 @@ static char *getprogpath(char ret[PATH_MAX], const char *bin) {
 /// GetMainExecutable - Return the path to the main executable, given the
 /// value of argv[0] from program startup.
 std::string getMainExecutable(const char *argv0, void *MainAddr) {
-#if defined(__APPLE__)
+#if defined(__wasi__)
+  return argv0;
+#elif defined(__APPLE__)
   // On OS X the executable path is saved to the stack by dyld. Reading it
   // from there is much faster than calling dladdr, especially for large
   // binaries with symbols.
@@ -505,7 +509,7 @@ static bool is_local_impl(struct STATVFS &Vfs) {
 #elif defined(__Fuchsia__)
   // Fuchsia doesn't yet support remote filesystem mounts.
   return true;
-#elif defined(__EMSCRIPTEN__)
+#elif defined(__EMSCRIPTEN__) || defined(__wasi__)
   // Emscripten doesn't currently support remote filesystem mounts.
   return true;
 #elif defined(__HAIKU__)
@@ -651,6 +655,7 @@ std::error_code equivalent(const Twine &A, const Twine &B, bool &result) {
 }
 
 static void expandTildeExpr(SmallVectorImpl<char> &Path) {
+#ifndef __wasi__
   StringRef PathStr(Path.begin(), Path.size());
   if (PathStr.empty() || !PathStr.starts_with("~"))
     return;
@@ -694,6 +699,7 @@ static void expandTildeExpr(SmallVectorImpl<char> &Path) {
   Path.clear();
   Path.append(Entry->pw_dir, Entry->pw_dir + strlen(Entry->pw_dir));
   llvm::sys::path::append(Path, Storage);
+#endif
 }
 
 void expand_tilde(const Twine &path, SmallVectorImpl<char> &dest) {
@@ -770,11 +776,15 @@ std::error_code status(int FD, file_status &Result) {
 }
 
 unsigned getUmask() {
+#ifdef __wasi__
+  return 0644;
+#else
   // Chose arbitary new mask and reset the umask to the old mask.
   // umask(2) never fails so ignore the return of the second call.
   unsigned Mask = ::umask(0);
   (void)::umask(Mask);
   return Mask;
+#endif
 }
 
 std::error_code setPermissions(const Twine &Path, perms Permissions) {
@@ -829,6 +839,9 @@ std::error_code setLastAccessAndModificationTime(int FD, TimePoint<> AccessTime,
 
 std::error_code mapped_file_region::init(int FD, uint64_t Offset,
                                          mapmode Mode) {
+#ifdef __wasi__
+  return std::error_code(ENOTSUP, std::generic_category());
+#else
   assert(Size != 0);
 
   int flags = (Mode == readwrite) ? MAP_SHARED : MAP_PRIVATE;
@@ -860,6 +873,7 @@ std::error_code mapped_file_region::init(int FD, uint64_t Offset,
   if (Mapping == MAP_FAILED)
     return errnoAsErrorCode();
   return std::error_code();
+#endif
 }
 
 mapped_file_region::mapped_file_region(int fd, mapmode mode, size_t length,
@@ -872,11 +886,14 @@ mapped_file_region::mapped_file_region(int fd, mapmode mode, size_t length,
 }
 
 void mapped_file_region::unmapImpl() {
+#ifndef __wasi__
   if (Mapping)
     ::munmap(Mapping, Size);
+#endif
 }
 
 void mapped_file_region::dontNeedImpl() {
+#ifndef __wasi__
   assert(Mode == mapped_file_region::readonly);
   if (!Mapping)
     return;
@@ -887,6 +904,7 @@ void mapped_file_region::dontNeedImpl() {
 #else
   ::madvise(Mapping, Size, MADV_DONTNEED);
 #endif
+#endif
 }
 
 int mapped_file_region::alignment() { return Process::getPageSizeEstimate(); }
@@ -920,7 +938,7 @@ static file_type direntType(dirent *Entry) {
   // Note that while glibc provides a macro to see if this is supported,
   // _DIRENT_HAVE_D_TYPE, it's not defined on BSD/Mac, so we test for the
   // d_type-to-mode_t conversion macro instead.
-#if defined(DTTOIF)
+#if defined(DTTOIF) && !defined(__wasi__)
   return typeForMode(DTTOIF(Entry->d_type));
 #else
   // Other platforms such as Solaris require a stat() to get the type.
@@ -1224,6 +1242,9 @@ Expected<size_t> readNativeFileSlice(file_t FD, MutableArrayRef<char> Buf,
 }
 
 std::error_code tryLockFile(int FD, std::chrono::milliseconds Timeout) {
+#if defined(__wasi__)
+  return std::error_code();
+#else
   auto Start = std::chrono::steady_clock::now();
   auto End = Start + Timeout;
   do {
@@ -1241,9 +1262,13 @@ std::error_code tryLockFile(int FD, std::chrono::milliseconds Timeout) {
     usleep(1000);
   } while (std::chrono::steady_clock::now() < End);
   return make_error_code(errc::no_lock_available);
+#endif
 }
 
 std::error_code lockFile(int FD) {
+#if defined(__wasi__)
+  return std::error_code();
+#else
   struct flock Lock;
   memset(&Lock, 0, sizeof(Lock));
   Lock.l_type = F_WRLCK;
@@ -1253,9 +1278,13 @@ std::error_code lockFile(int FD) {
   if (::fcntl(FD, F_SETLKW, &Lock) != -1)
     return std::error_code();
   return errnoAsErrorCode();
+#endif
 }
 
 std::error_code unlockFile(int FD) {
+#if defined(__wasi__)
+  return std::error_code();
+#else
   struct flock Lock;
   Lock.l_type = F_UNLCK;
   Lock.l_whence = SEEK_SET;
@@ -1264,6 +1293,7 @@ std::error_code unlockFile(int FD) {
   if (::fcntl(FD, F_SETLK, ...
[truncated]

``````````

</details>


https://github.com/llvm/llvm-project/pull/91051


More information about the libcxx-commits mailing list