Skip to content

Conversation

@perry-ca
Copy link
Contributor

In this PR I'm changing the way we provide the missing functions like strnlen() on z/OS from the separate header file to a wrapper around the system headers that declare these functions. This will be less intrusive.

@perry-ca perry-ca requested a review from abhina-sree November 12, 2025 15:34
@llvmbot llvmbot added clang Clang issues not falling into any other category clang:frontend Language frontend issues, e.g. anything involving "Sema" tools:llvm-exegesis llvm:support objectyaml llvm:binary-utilities clang:bytecode Issues for the clang bytecode constexpr interpreter labels Nov 12, 2025
@perry-ca perry-ca requested a review from zibi2 November 12, 2025 15:34
@llvmbot
Copy link
Member

llvmbot commented Nov 12, 2025

@llvm/pr-subscribers-objectyaml
@llvm/pr-subscribers-clang
@llvm/pr-subscribers-llvm-support

@llvm/pr-subscribers-tools-llvm-exegesis

Author: Sean Perry (perry-ca)

Changes

In this PR I'm changing the way we provide the missing functions like strnlen() on z/OS from the separate header file to a wrapper around the system headers that declare these functions. This will be less intrusive.


Full diff: https://github.com/llvm/llvm-project/pull/167703.diff

17 Files Affected:

  • (modified) clang/lib/AST/ByteCode/Context.cpp (-1)
  • (modified) llvm/CMakeLists.txt (+5)
  • (removed) llvm/include/llvm/Support/SystemZ/zOSSupport.h (-47)
  • (added) llvm/include/llvm/Support/SystemZ/zos_wrappers/string.h (+35)
  • (modified) llvm/lib/ObjCopy/MachO/MachOLayoutBuilder.cpp (-1)
  • (modified) llvm/lib/ObjCopy/MachO/MachOObject.cpp (-1)
  • (modified) llvm/lib/ObjCopy/MachO/MachOReader.cpp (-1)
  • (modified) llvm/lib/ObjectYAML/MachOEmitter.cpp (-1)
  • (modified) llvm/lib/ObjectYAML/MachOYAML.cpp (-1)
  • (modified) llvm/lib/Support/CMakeLists.txt (+1)
  • (modified) llvm/lib/Support/Unix/Program.inc (-1)
  • (added) llvm/lib/Support/zOSLibFunctions.cpp (+82)
  • (modified) llvm/tools/llvm-exegesis/lib/BenchmarkRunner.cpp (-1)
  • (modified) llvm/tools/llvm-exegesis/lib/Error.cpp (-1)
  • (modified) llvm/tools/llvm-readobj/ELFDumper.cpp (-1)
  • (modified) llvm/tools/llvm-readobj/ObjDumper.cpp (-1)
  • (modified) llvm/tools/obj2yaml/macho2yaml.cpp (-1)
diff --git a/clang/lib/AST/ByteCode/Context.cpp b/clang/lib/AST/ByteCode/Context.cpp
index 12bf3a3954b1b..74ec986e49ca7 100644
--- a/clang/lib/AST/ByteCode/Context.cpp
+++ b/clang/lib/AST/ByteCode/Context.cpp
@@ -21,7 +21,6 @@
 #include "clang/AST/ASTLambda.h"
 #include "clang/AST/Expr.h"
 #include "clang/Basic/TargetInfo.h"
-#include "llvm/Support/SystemZ/zOSSupport.h"
 
 using namespace clang;
 using namespace clang::interp;
diff --git a/llvm/CMakeLists.txt b/llvm/CMakeLists.txt
index f192cd05b5a34..eac38f3e17572 100644
--- a/llvm/CMakeLists.txt
+++ b/llvm/CMakeLists.txt
@@ -1294,6 +1294,11 @@ if(LLVM_TARGET_IS_CROSSCOMPILE_HOST)
 # (this is a variable that CrossCompile sets on recursive invocations)
 endif()
 
+# Special hack for z/OS for missing POSIX functions
+if (CMAKE_SYSTEM_NAME MATCHES "OS390")
+  include_directories(SYSTEM "${LLVM_MAIN_INCLUDE_DIR}/llvm/Support/SystemZ/zos_wrappers" )
+endif()
+
 if( "${CMAKE_SYSTEM_NAME}" MATCHES SunOS )
    # special hack for Solaris to handle crazy system sys/regset.h
    include_directories("${LLVM_MAIN_INCLUDE_DIR}/llvm/Support/Solaris")
diff --git a/llvm/include/llvm/Support/SystemZ/zOSSupport.h b/llvm/include/llvm/Support/SystemZ/zOSSupport.h
deleted file mode 100644
index f9a61f887d5dd..0000000000000
--- a/llvm/include/llvm/Support/SystemZ/zOSSupport.h
+++ /dev/null
@@ -1,47 +0,0 @@
-//===- zOSSupport.h - Common z/OS Include File ------------------*- 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
-//
-//===----------------------------------------------------------------------===//
-//
-// This file defines z/OS implementations for common functions.
-//
-//===----------------------------------------------------------------------===//
-
-#ifndef LLVM_SUPPORT_ZOSSUPPORT_H
-#define LLVM_SUPPORT_ZOSSUPPORT_H
-
-#ifdef __MVS__
-#include <sys/resource.h>
-#include <sys/wait.h>
-
-// z/OS Unix System Services does not have strsignal() support, so the
-// strsignal() function is implemented here.
-inline char *strsignal(int sig) {
-  static char msg[256];
-  sprintf(msg, "%d", sig);
-  return msg;
-}
-
-// z/OS Unix System Services does not have wait4() support, so the wait4
-// function is implemented here.
-inline pid_t wait4(pid_t pid, int *wstatus, int options,
-                   struct rusage *rusage) {
-  pid_t Result = waitpid(pid, wstatus, options);
-  int GetrusageRC = getrusage(RUSAGE_CHILDREN, rusage);
-  assert(!GetrusageRC && "Must have valid measure of the resources!");
-  return Result;
-}
-
-// z/OS Unix System Services does not have strnlen() support, so the strnlen()
-// function is implemented here.
-inline std::size_t strnlen(const char *S, std::size_t MaxLen) {
-  const char *PtrToNullChar =
-      static_cast<const char *>(std::memchr(S, '\0', MaxLen));
-  return PtrToNullChar ? PtrToNullChar - S : MaxLen;
-}
-
-#endif
-#endif
diff --git a/llvm/include/llvm/Support/SystemZ/zos_wrappers/string.h b/llvm/include/llvm/Support/SystemZ/zos_wrappers/string.h
new file mode 100644
index 0000000000000..5b998e16431bd
--- /dev/null
+++ b/llvm/include/llvm/Support/SystemZ/zos_wrappers/string.h
@@ -0,0 +1,35 @@
+//===- string.h - Common z/OS Include File ----------------------*- 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
+//
+//===----------------------------------------------------------------------===//
+//
+// This file declares z/OS implementations for common functions.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_SUPPORT_ZOSWRAPPER_STRING_H
+#define LLVM_SUPPORT_ZOSWRAPPER_STRING_H
+
+#include_next <string.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+// z/OS Unix System Services does not have support for:
+// - strsignal()
+// - strnlen()
+// Implementations are provided for z/OS.
+
+char *strsignal(int sig) asm("llvm_zos_strsignal");
+
+size_t strnlen(const char *S, size_t MaxLen) asm("llvm_zos_strnlen");
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
diff --git a/llvm/lib/ObjCopy/MachO/MachOLayoutBuilder.cpp b/llvm/lib/ObjCopy/MachO/MachOLayoutBuilder.cpp
index 93bc6631e64c8..8660c903c617d 100644
--- a/llvm/lib/ObjCopy/MachO/MachOLayoutBuilder.cpp
+++ b/llvm/lib/ObjCopy/MachO/MachOLayoutBuilder.cpp
@@ -10,7 +10,6 @@
 #include "llvm/Support/Alignment.h"
 #include "llvm/Support/Errc.h"
 #include "llvm/Support/ErrorHandling.h"
-#include "llvm/Support/SystemZ/zOSSupport.h"
 
 using namespace llvm;
 using namespace llvm::objcopy::macho;
diff --git a/llvm/lib/ObjCopy/MachO/MachOObject.cpp b/llvm/lib/ObjCopy/MachO/MachOObject.cpp
index 8d2c02dc37c99..8f7f54c99bddc 100644
--- a/llvm/lib/ObjCopy/MachO/MachOObject.cpp
+++ b/llvm/lib/ObjCopy/MachO/MachOObject.cpp
@@ -8,7 +8,6 @@
 
 #include "MachOObject.h"
 #include "llvm/ADT/SmallPtrSet.h"
-#include "llvm/Support/SystemZ/zOSSupport.h"
 #include <unordered_set>
 
 using namespace llvm;
diff --git a/llvm/lib/ObjCopy/MachO/MachOReader.cpp b/llvm/lib/ObjCopy/MachO/MachOReader.cpp
index 2b344f36d8e78..dd4d60deccbb8 100644
--- a/llvm/lib/ObjCopy/MachO/MachOReader.cpp
+++ b/llvm/lib/ObjCopy/MachO/MachOReader.cpp
@@ -10,7 +10,6 @@
 #include "MachOObject.h"
 #include "llvm/BinaryFormat/MachO.h"
 #include "llvm/Object/MachO.h"
-#include "llvm/Support/SystemZ/zOSSupport.h"
 #include <memory>
 
 using namespace llvm;
diff --git a/llvm/lib/ObjectYAML/MachOEmitter.cpp b/llvm/lib/ObjectYAML/MachOEmitter.cpp
index 35d442e8e3437..e32de0b288fe4 100644
--- a/llvm/lib/ObjectYAML/MachOEmitter.cpp
+++ b/llvm/lib/ObjectYAML/MachOEmitter.cpp
@@ -20,7 +20,6 @@
 #include "llvm/Support/FormatVariadic.h"
 #include "llvm/Support/LEB128.h"
 #include "llvm/Support/YAMLTraits.h"
-#include "llvm/Support/SystemZ/zOSSupport.h"
 #include "llvm/Support/raw_ostream.h"
 
 using namespace llvm;
diff --git a/llvm/lib/ObjectYAML/MachOYAML.cpp b/llvm/lib/ObjectYAML/MachOYAML.cpp
index 133358d395928..32015ddeb3618 100644
--- a/llvm/lib/ObjectYAML/MachOYAML.cpp
+++ b/llvm/lib/ObjectYAML/MachOYAML.cpp
@@ -15,7 +15,6 @@
 #include "llvm/BinaryFormat/MachO.h"
 #include "llvm/Support/YAMLTraits.h"
 #include "llvm/Support/raw_ostream.h"
-#include "llvm/Support/SystemZ/zOSSupport.h"
 #include "llvm/TargetParser/Host.h"
 #include <cstdint>
 #include <cstring>
diff --git a/llvm/lib/Support/CMakeLists.txt b/llvm/lib/Support/CMakeLists.txt
index 671a5fe941cef..a0980bda2a212 100644
--- a/llvm/lib/Support/CMakeLists.txt
+++ b/llvm/lib/Support/CMakeLists.txt
@@ -311,6 +311,7 @@ add_llvm_component_library(LLVMSupport
   Threading.cpp
   Valgrind.cpp
   Watchdog.cpp
+  zOSLibFunctions.cpp
 
   ADDITIONAL_HEADER_DIRS
   Unix
diff --git a/llvm/lib/Support/Unix/Program.inc b/llvm/lib/Support/Unix/Program.inc
index 4f17b2257a756..1b5e7bd6403a1 100644
--- a/llvm/lib/Support/Unix/Program.inc
+++ b/llvm/lib/Support/Unix/Program.inc
@@ -26,7 +26,6 @@
 #include "llvm/Support/FileSystem.h"
 #include "llvm/Support/Path.h"
 #include "llvm/Support/StringSaver.h"
-#include "llvm/Support/SystemZ/zOSSupport.h"
 #include "llvm/Support/raw_ostream.h"
 #include <sys/stat.h>
 #include <sys/resource.h>
diff --git a/llvm/lib/Support/zOSLibFunctions.cpp b/llvm/lib/Support/zOSLibFunctions.cpp
new file mode 100644
index 0000000000000..c80d80633de5d
--- /dev/null
+++ b/llvm/lib/Support/zOSLibFunctions.cpp
@@ -0,0 +1,82 @@
+//===-- zOSLibFunctions.cpp -----------------------------------------------===//
+////
+//// 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
+////
+////===--------------------------------------------------------------------===//
+
+//===----------------------------------------------------------------------===//
+//
+// This file defines z/OS implementations for common functions.
+//
+//===----------------------------------------------------------------------===//
+
+#ifdef __MVS__
+#include <stdio.h>
+#include <string.h>
+#include <sys/resource.h>
+#include <sys/wait.h>
+
+
+const char *signalName[] = {
+  /*  0 */ nullptr,
+  /*  1 */ "Hangup",                     // SIGHUP
+  /*  2 */ "Interrupt",                  // SIGINT
+  /*  3 */ "Aborted",                    // SIGABRT
+  /*  4 */ "Illegal instruction",        // SIGILL
+  /*  5 */ "Polling event",              // SIGPOLL
+  /*  6 */ "Socket data available",      // SIGURG
+  /*  7 */ "Stopped (signal)",           // SIGSTOP
+  /*  8 */ "Floating point exception",   // SIGFPE
+  /*  9 */ "Killed",                     // SIGKILL
+  /* 10 */ "Bus error",                  // SIGBUS
+  /* 11 */ "Segmentation fault",         // SIGSEGV
+  /* 12 */ "Bad system call",            // SIGSYS
+  /* 13 */ "Broken pipe",                // SIGPIPE
+  /* 14 */ "Alarm clock",                // SIGALRM
+  /* 15 */ "Terminated",                 // SIGTERM
+  /* 16 */ "User defined signal 1",      // SIGUSR1
+  /* 17 */ "User defined signal 2",      // SIGUSR2
+  /* 18 */ "Abend",                      // SIGABND
+  /* 19 */ "Continued",                  // SIGCONT
+  /* 20 */ "Child exited",               // SIGCHLD
+  /* 21 */ "Stopped (tty input)",        // SIGTTIN
+  /* 22 */ "Stopped (tty output)",       // SIGTTOU
+  /* 23 */ "I/O complete",               // SIGIO
+  /* 24 */ "Quit",                       // SIGQUIT
+  /* 25 */ "Stopped",                    // SIGTSTP
+  /* 26 */ "Trace/breakpoint trap",      // SIGTRAP
+  /* 27 */ "I/O error",                  // SIGIOERR
+  /* 28 */ "Window changed",             // SIGWINCH
+  /* 29 */ "CPU time limit exceeded",    // SIGXCPU
+  /* 30 */ "File size limit exceeded",   // SIGXFSZ
+  /* 31 */ "Virtual timer expired",      // SIGVTALRM
+  /* 32 */ "Profiling timer expired",    // SIGPROF
+  /* 33 */ "OMVS subsystem shutdown",    // SIGDANGER
+  /* 34 */ "Thread stop",                // SIGTHSTOP
+  /* 35 */ "Thread resume",              // SIGTHCONT
+  /* 36 */ nullptr,
+  /* 37 */ "Toggle syscall trace",       // SIGTRACE
+  /* 38 */ nullptr,                      // SIGDCE
+  /* 39 */ "System dump",                // SIGDUMP
+};
+
+// z/OS Unix System Services does not have strsignal() support, so the
+// strsignal() function is implemented here.
+char *strsignal(int sig) {
+  if (static_cast<size_t>(sig) < sizeof(signalName)/sizeof(signalName[0]) && signalName[sig])
+    return const_cast<char *>(signalName[sig]);
+  static char msg[256];
+  sprintf(msg, "Unknown signal %d", sig);
+  return msg;
+}
+
+// z/OS Unix System Services does not have strnlen() support, so the strnlen()
+// function is implemented here.
+size_t strnlen(const char *S, size_t MaxLen) {
+  const char *PtrToNullChar =
+      static_cast<const char *>(memchr(S, '\0', MaxLen));
+  return PtrToNullChar ? PtrToNullChar - S : MaxLen;
+}
+#endif
diff --git a/llvm/tools/llvm-exegesis/lib/BenchmarkRunner.cpp b/llvm/tools/llvm-exegesis/lib/BenchmarkRunner.cpp
index 12fad7d57444f..a86be13f24882 100644
--- a/llvm/tools/llvm-exegesis/lib/BenchmarkRunner.cpp
+++ b/llvm/tools/llvm-exegesis/lib/BenchmarkRunner.cpp
@@ -27,7 +27,6 @@
 #include "llvm/Support/MemoryBuffer.h"
 #include "llvm/Support/Program.h"
 #include "llvm/Support/Signals.h"
-#include "llvm/Support/SystemZ/zOSSupport.h"
 #include <cmath>
 #include <memory>
 #include <string>
diff --git a/llvm/tools/llvm-exegesis/lib/Error.cpp b/llvm/tools/llvm-exegesis/lib/Error.cpp
index 2908df25ddb1a..9024ba5ceb524 100644
--- a/llvm/tools/llvm-exegesis/lib/Error.cpp
+++ b/llvm/tools/llvm-exegesis/lib/Error.cpp
@@ -10,7 +10,6 @@
 #include "llvm/Config/llvm-config.h" // for LLVM_ON_UNIX
 
 #ifdef LLVM_ON_UNIX
-#include "llvm/Support/SystemZ/zOSSupport.h"
 #include <string.h>
 #endif // LLVM_ON_UNIX
 
diff --git a/llvm/tools/llvm-readobj/ELFDumper.cpp b/llvm/tools/llvm-readobj/ELFDumper.cpp
index 6f09da5a4099f..2b5bc631afd8d 100644
--- a/llvm/tools/llvm-readobj/ELFDumper.cpp
+++ b/llvm/tools/llvm-readobj/ELFDumper.cpp
@@ -61,7 +61,6 @@
 #include "llvm/Support/RISCVAttributeParser.h"
 #include "llvm/Support/RISCVAttributes.h"
 #include "llvm/Support/ScopedPrinter.h"
-#include "llvm/Support/SystemZ/zOSSupport.h"
 #include "llvm/Support/raw_ostream.h"
 #include <algorithm>
 #include <array>
diff --git a/llvm/tools/llvm-readobj/ObjDumper.cpp b/llvm/tools/llvm-readobj/ObjDumper.cpp
index 20e027aa5a5ef..1d193573b4776 100644
--- a/llvm/tools/llvm-readobj/ObjDumper.cpp
+++ b/llvm/tools/llvm-readobj/ObjDumper.cpp
@@ -21,7 +21,6 @@
 #include "llvm/Support/Error.h"
 #include "llvm/Support/FormatVariadic.h"
 #include "llvm/Support/ScopedPrinter.h"
-#include "llvm/Support/SystemZ/zOSSupport.h"
 #include "llvm/Support/raw_ostream.h"
 #include <map>
 
diff --git a/llvm/tools/obj2yaml/macho2yaml.cpp b/llvm/tools/obj2yaml/macho2yaml.cpp
index 00220123e8189..f78ec8f3c265a 100644
--- a/llvm/tools/obj2yaml/macho2yaml.cpp
+++ b/llvm/tools/obj2yaml/macho2yaml.cpp
@@ -15,7 +15,6 @@
 #include "llvm/Support/Error.h"
 #include "llvm/Support/ErrorHandling.h"
 #include "llvm/Support/LEB128.h"
-#include "llvm/Support/SystemZ/zOSSupport.h"
 
 #include <string.h> // for memcpy
 

@llvmbot
Copy link
Member

llvmbot commented Nov 12, 2025

@llvm/pr-subscribers-llvm-binary-utilities

Author: Sean Perry (perry-ca)

Changes

In this PR I'm changing the way we provide the missing functions like strnlen() on z/OS from the separate header file to a wrapper around the system headers that declare these functions. This will be less intrusive.


Full diff: https://github.com/llvm/llvm-project/pull/167703.diff

17 Files Affected:

  • (modified) clang/lib/AST/ByteCode/Context.cpp (-1)
  • (modified) llvm/CMakeLists.txt (+5)
  • (removed) llvm/include/llvm/Support/SystemZ/zOSSupport.h (-47)
  • (added) llvm/include/llvm/Support/SystemZ/zos_wrappers/string.h (+35)
  • (modified) llvm/lib/ObjCopy/MachO/MachOLayoutBuilder.cpp (-1)
  • (modified) llvm/lib/ObjCopy/MachO/MachOObject.cpp (-1)
  • (modified) llvm/lib/ObjCopy/MachO/MachOReader.cpp (-1)
  • (modified) llvm/lib/ObjectYAML/MachOEmitter.cpp (-1)
  • (modified) llvm/lib/ObjectYAML/MachOYAML.cpp (-1)
  • (modified) llvm/lib/Support/CMakeLists.txt (+1)
  • (modified) llvm/lib/Support/Unix/Program.inc (-1)
  • (added) llvm/lib/Support/zOSLibFunctions.cpp (+82)
  • (modified) llvm/tools/llvm-exegesis/lib/BenchmarkRunner.cpp (-1)
  • (modified) llvm/tools/llvm-exegesis/lib/Error.cpp (-1)
  • (modified) llvm/tools/llvm-readobj/ELFDumper.cpp (-1)
  • (modified) llvm/tools/llvm-readobj/ObjDumper.cpp (-1)
  • (modified) llvm/tools/obj2yaml/macho2yaml.cpp (-1)
diff --git a/clang/lib/AST/ByteCode/Context.cpp b/clang/lib/AST/ByteCode/Context.cpp
index 12bf3a3954b1b..74ec986e49ca7 100644
--- a/clang/lib/AST/ByteCode/Context.cpp
+++ b/clang/lib/AST/ByteCode/Context.cpp
@@ -21,7 +21,6 @@
 #include "clang/AST/ASTLambda.h"
 #include "clang/AST/Expr.h"
 #include "clang/Basic/TargetInfo.h"
-#include "llvm/Support/SystemZ/zOSSupport.h"
 
 using namespace clang;
 using namespace clang::interp;
diff --git a/llvm/CMakeLists.txt b/llvm/CMakeLists.txt
index f192cd05b5a34..eac38f3e17572 100644
--- a/llvm/CMakeLists.txt
+++ b/llvm/CMakeLists.txt
@@ -1294,6 +1294,11 @@ if(LLVM_TARGET_IS_CROSSCOMPILE_HOST)
 # (this is a variable that CrossCompile sets on recursive invocations)
 endif()
 
+# Special hack for z/OS for missing POSIX functions
+if (CMAKE_SYSTEM_NAME MATCHES "OS390")
+  include_directories(SYSTEM "${LLVM_MAIN_INCLUDE_DIR}/llvm/Support/SystemZ/zos_wrappers" )
+endif()
+
 if( "${CMAKE_SYSTEM_NAME}" MATCHES SunOS )
    # special hack for Solaris to handle crazy system sys/regset.h
    include_directories("${LLVM_MAIN_INCLUDE_DIR}/llvm/Support/Solaris")
diff --git a/llvm/include/llvm/Support/SystemZ/zOSSupport.h b/llvm/include/llvm/Support/SystemZ/zOSSupport.h
deleted file mode 100644
index f9a61f887d5dd..0000000000000
--- a/llvm/include/llvm/Support/SystemZ/zOSSupport.h
+++ /dev/null
@@ -1,47 +0,0 @@
-//===- zOSSupport.h - Common z/OS Include File ------------------*- 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
-//
-//===----------------------------------------------------------------------===//
-//
-// This file defines z/OS implementations for common functions.
-//
-//===----------------------------------------------------------------------===//
-
-#ifndef LLVM_SUPPORT_ZOSSUPPORT_H
-#define LLVM_SUPPORT_ZOSSUPPORT_H
-
-#ifdef __MVS__
-#include <sys/resource.h>
-#include <sys/wait.h>
-
-// z/OS Unix System Services does not have strsignal() support, so the
-// strsignal() function is implemented here.
-inline char *strsignal(int sig) {
-  static char msg[256];
-  sprintf(msg, "%d", sig);
-  return msg;
-}
-
-// z/OS Unix System Services does not have wait4() support, so the wait4
-// function is implemented here.
-inline pid_t wait4(pid_t pid, int *wstatus, int options,
-                   struct rusage *rusage) {
-  pid_t Result = waitpid(pid, wstatus, options);
-  int GetrusageRC = getrusage(RUSAGE_CHILDREN, rusage);
-  assert(!GetrusageRC && "Must have valid measure of the resources!");
-  return Result;
-}
-
-// z/OS Unix System Services does not have strnlen() support, so the strnlen()
-// function is implemented here.
-inline std::size_t strnlen(const char *S, std::size_t MaxLen) {
-  const char *PtrToNullChar =
-      static_cast<const char *>(std::memchr(S, '\0', MaxLen));
-  return PtrToNullChar ? PtrToNullChar - S : MaxLen;
-}
-
-#endif
-#endif
diff --git a/llvm/include/llvm/Support/SystemZ/zos_wrappers/string.h b/llvm/include/llvm/Support/SystemZ/zos_wrappers/string.h
new file mode 100644
index 0000000000000..5b998e16431bd
--- /dev/null
+++ b/llvm/include/llvm/Support/SystemZ/zos_wrappers/string.h
@@ -0,0 +1,35 @@
+//===- string.h - Common z/OS Include File ----------------------*- 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
+//
+//===----------------------------------------------------------------------===//
+//
+// This file declares z/OS implementations for common functions.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_SUPPORT_ZOSWRAPPER_STRING_H
+#define LLVM_SUPPORT_ZOSWRAPPER_STRING_H
+
+#include_next <string.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+// z/OS Unix System Services does not have support for:
+// - strsignal()
+// - strnlen()
+// Implementations are provided for z/OS.
+
+char *strsignal(int sig) asm("llvm_zos_strsignal");
+
+size_t strnlen(const char *S, size_t MaxLen) asm("llvm_zos_strnlen");
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
diff --git a/llvm/lib/ObjCopy/MachO/MachOLayoutBuilder.cpp b/llvm/lib/ObjCopy/MachO/MachOLayoutBuilder.cpp
index 93bc6631e64c8..8660c903c617d 100644
--- a/llvm/lib/ObjCopy/MachO/MachOLayoutBuilder.cpp
+++ b/llvm/lib/ObjCopy/MachO/MachOLayoutBuilder.cpp
@@ -10,7 +10,6 @@
 #include "llvm/Support/Alignment.h"
 #include "llvm/Support/Errc.h"
 #include "llvm/Support/ErrorHandling.h"
-#include "llvm/Support/SystemZ/zOSSupport.h"
 
 using namespace llvm;
 using namespace llvm::objcopy::macho;
diff --git a/llvm/lib/ObjCopy/MachO/MachOObject.cpp b/llvm/lib/ObjCopy/MachO/MachOObject.cpp
index 8d2c02dc37c99..8f7f54c99bddc 100644
--- a/llvm/lib/ObjCopy/MachO/MachOObject.cpp
+++ b/llvm/lib/ObjCopy/MachO/MachOObject.cpp
@@ -8,7 +8,6 @@
 
 #include "MachOObject.h"
 #include "llvm/ADT/SmallPtrSet.h"
-#include "llvm/Support/SystemZ/zOSSupport.h"
 #include <unordered_set>
 
 using namespace llvm;
diff --git a/llvm/lib/ObjCopy/MachO/MachOReader.cpp b/llvm/lib/ObjCopy/MachO/MachOReader.cpp
index 2b344f36d8e78..dd4d60deccbb8 100644
--- a/llvm/lib/ObjCopy/MachO/MachOReader.cpp
+++ b/llvm/lib/ObjCopy/MachO/MachOReader.cpp
@@ -10,7 +10,6 @@
 #include "MachOObject.h"
 #include "llvm/BinaryFormat/MachO.h"
 #include "llvm/Object/MachO.h"
-#include "llvm/Support/SystemZ/zOSSupport.h"
 #include <memory>
 
 using namespace llvm;
diff --git a/llvm/lib/ObjectYAML/MachOEmitter.cpp b/llvm/lib/ObjectYAML/MachOEmitter.cpp
index 35d442e8e3437..e32de0b288fe4 100644
--- a/llvm/lib/ObjectYAML/MachOEmitter.cpp
+++ b/llvm/lib/ObjectYAML/MachOEmitter.cpp
@@ -20,7 +20,6 @@
 #include "llvm/Support/FormatVariadic.h"
 #include "llvm/Support/LEB128.h"
 #include "llvm/Support/YAMLTraits.h"
-#include "llvm/Support/SystemZ/zOSSupport.h"
 #include "llvm/Support/raw_ostream.h"
 
 using namespace llvm;
diff --git a/llvm/lib/ObjectYAML/MachOYAML.cpp b/llvm/lib/ObjectYAML/MachOYAML.cpp
index 133358d395928..32015ddeb3618 100644
--- a/llvm/lib/ObjectYAML/MachOYAML.cpp
+++ b/llvm/lib/ObjectYAML/MachOYAML.cpp
@@ -15,7 +15,6 @@
 #include "llvm/BinaryFormat/MachO.h"
 #include "llvm/Support/YAMLTraits.h"
 #include "llvm/Support/raw_ostream.h"
-#include "llvm/Support/SystemZ/zOSSupport.h"
 #include "llvm/TargetParser/Host.h"
 #include <cstdint>
 #include <cstring>
diff --git a/llvm/lib/Support/CMakeLists.txt b/llvm/lib/Support/CMakeLists.txt
index 671a5fe941cef..a0980bda2a212 100644
--- a/llvm/lib/Support/CMakeLists.txt
+++ b/llvm/lib/Support/CMakeLists.txt
@@ -311,6 +311,7 @@ add_llvm_component_library(LLVMSupport
   Threading.cpp
   Valgrind.cpp
   Watchdog.cpp
+  zOSLibFunctions.cpp
 
   ADDITIONAL_HEADER_DIRS
   Unix
diff --git a/llvm/lib/Support/Unix/Program.inc b/llvm/lib/Support/Unix/Program.inc
index 4f17b2257a756..1b5e7bd6403a1 100644
--- a/llvm/lib/Support/Unix/Program.inc
+++ b/llvm/lib/Support/Unix/Program.inc
@@ -26,7 +26,6 @@
 #include "llvm/Support/FileSystem.h"
 #include "llvm/Support/Path.h"
 #include "llvm/Support/StringSaver.h"
-#include "llvm/Support/SystemZ/zOSSupport.h"
 #include "llvm/Support/raw_ostream.h"
 #include <sys/stat.h>
 #include <sys/resource.h>
diff --git a/llvm/lib/Support/zOSLibFunctions.cpp b/llvm/lib/Support/zOSLibFunctions.cpp
new file mode 100644
index 0000000000000..c80d80633de5d
--- /dev/null
+++ b/llvm/lib/Support/zOSLibFunctions.cpp
@@ -0,0 +1,82 @@
+//===-- zOSLibFunctions.cpp -----------------------------------------------===//
+////
+//// 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
+////
+////===--------------------------------------------------------------------===//
+
+//===----------------------------------------------------------------------===//
+//
+// This file defines z/OS implementations for common functions.
+//
+//===----------------------------------------------------------------------===//
+
+#ifdef __MVS__
+#include <stdio.h>
+#include <string.h>
+#include <sys/resource.h>
+#include <sys/wait.h>
+
+
+const char *signalName[] = {
+  /*  0 */ nullptr,
+  /*  1 */ "Hangup",                     // SIGHUP
+  /*  2 */ "Interrupt",                  // SIGINT
+  /*  3 */ "Aborted",                    // SIGABRT
+  /*  4 */ "Illegal instruction",        // SIGILL
+  /*  5 */ "Polling event",              // SIGPOLL
+  /*  6 */ "Socket data available",      // SIGURG
+  /*  7 */ "Stopped (signal)",           // SIGSTOP
+  /*  8 */ "Floating point exception",   // SIGFPE
+  /*  9 */ "Killed",                     // SIGKILL
+  /* 10 */ "Bus error",                  // SIGBUS
+  /* 11 */ "Segmentation fault",         // SIGSEGV
+  /* 12 */ "Bad system call",            // SIGSYS
+  /* 13 */ "Broken pipe",                // SIGPIPE
+  /* 14 */ "Alarm clock",                // SIGALRM
+  /* 15 */ "Terminated",                 // SIGTERM
+  /* 16 */ "User defined signal 1",      // SIGUSR1
+  /* 17 */ "User defined signal 2",      // SIGUSR2
+  /* 18 */ "Abend",                      // SIGABND
+  /* 19 */ "Continued",                  // SIGCONT
+  /* 20 */ "Child exited",               // SIGCHLD
+  /* 21 */ "Stopped (tty input)",        // SIGTTIN
+  /* 22 */ "Stopped (tty output)",       // SIGTTOU
+  /* 23 */ "I/O complete",               // SIGIO
+  /* 24 */ "Quit",                       // SIGQUIT
+  /* 25 */ "Stopped",                    // SIGTSTP
+  /* 26 */ "Trace/breakpoint trap",      // SIGTRAP
+  /* 27 */ "I/O error",                  // SIGIOERR
+  /* 28 */ "Window changed",             // SIGWINCH
+  /* 29 */ "CPU time limit exceeded",    // SIGXCPU
+  /* 30 */ "File size limit exceeded",   // SIGXFSZ
+  /* 31 */ "Virtual timer expired",      // SIGVTALRM
+  /* 32 */ "Profiling timer expired",    // SIGPROF
+  /* 33 */ "OMVS subsystem shutdown",    // SIGDANGER
+  /* 34 */ "Thread stop",                // SIGTHSTOP
+  /* 35 */ "Thread resume",              // SIGTHCONT
+  /* 36 */ nullptr,
+  /* 37 */ "Toggle syscall trace",       // SIGTRACE
+  /* 38 */ nullptr,                      // SIGDCE
+  /* 39 */ "System dump",                // SIGDUMP
+};
+
+// z/OS Unix System Services does not have strsignal() support, so the
+// strsignal() function is implemented here.
+char *strsignal(int sig) {
+  if (static_cast<size_t>(sig) < sizeof(signalName)/sizeof(signalName[0]) && signalName[sig])
+    return const_cast<char *>(signalName[sig]);
+  static char msg[256];
+  sprintf(msg, "Unknown signal %d", sig);
+  return msg;
+}
+
+// z/OS Unix System Services does not have strnlen() support, so the strnlen()
+// function is implemented here.
+size_t strnlen(const char *S, size_t MaxLen) {
+  const char *PtrToNullChar =
+      static_cast<const char *>(memchr(S, '\0', MaxLen));
+  return PtrToNullChar ? PtrToNullChar - S : MaxLen;
+}
+#endif
diff --git a/llvm/tools/llvm-exegesis/lib/BenchmarkRunner.cpp b/llvm/tools/llvm-exegesis/lib/BenchmarkRunner.cpp
index 12fad7d57444f..a86be13f24882 100644
--- a/llvm/tools/llvm-exegesis/lib/BenchmarkRunner.cpp
+++ b/llvm/tools/llvm-exegesis/lib/BenchmarkRunner.cpp
@@ -27,7 +27,6 @@
 #include "llvm/Support/MemoryBuffer.h"
 #include "llvm/Support/Program.h"
 #include "llvm/Support/Signals.h"
-#include "llvm/Support/SystemZ/zOSSupport.h"
 #include <cmath>
 #include <memory>
 #include <string>
diff --git a/llvm/tools/llvm-exegesis/lib/Error.cpp b/llvm/tools/llvm-exegesis/lib/Error.cpp
index 2908df25ddb1a..9024ba5ceb524 100644
--- a/llvm/tools/llvm-exegesis/lib/Error.cpp
+++ b/llvm/tools/llvm-exegesis/lib/Error.cpp
@@ -10,7 +10,6 @@
 #include "llvm/Config/llvm-config.h" // for LLVM_ON_UNIX
 
 #ifdef LLVM_ON_UNIX
-#include "llvm/Support/SystemZ/zOSSupport.h"
 #include <string.h>
 #endif // LLVM_ON_UNIX
 
diff --git a/llvm/tools/llvm-readobj/ELFDumper.cpp b/llvm/tools/llvm-readobj/ELFDumper.cpp
index 6f09da5a4099f..2b5bc631afd8d 100644
--- a/llvm/tools/llvm-readobj/ELFDumper.cpp
+++ b/llvm/tools/llvm-readobj/ELFDumper.cpp
@@ -61,7 +61,6 @@
 #include "llvm/Support/RISCVAttributeParser.h"
 #include "llvm/Support/RISCVAttributes.h"
 #include "llvm/Support/ScopedPrinter.h"
-#include "llvm/Support/SystemZ/zOSSupport.h"
 #include "llvm/Support/raw_ostream.h"
 #include <algorithm>
 #include <array>
diff --git a/llvm/tools/llvm-readobj/ObjDumper.cpp b/llvm/tools/llvm-readobj/ObjDumper.cpp
index 20e027aa5a5ef..1d193573b4776 100644
--- a/llvm/tools/llvm-readobj/ObjDumper.cpp
+++ b/llvm/tools/llvm-readobj/ObjDumper.cpp
@@ -21,7 +21,6 @@
 #include "llvm/Support/Error.h"
 #include "llvm/Support/FormatVariadic.h"
 #include "llvm/Support/ScopedPrinter.h"
-#include "llvm/Support/SystemZ/zOSSupport.h"
 #include "llvm/Support/raw_ostream.h"
 #include <map>
 
diff --git a/llvm/tools/obj2yaml/macho2yaml.cpp b/llvm/tools/obj2yaml/macho2yaml.cpp
index 00220123e8189..f78ec8f3c265a 100644
--- a/llvm/tools/obj2yaml/macho2yaml.cpp
+++ b/llvm/tools/obj2yaml/macho2yaml.cpp
@@ -15,7 +15,6 @@
 #include "llvm/Support/Error.h"
 #include "llvm/Support/ErrorHandling.h"
 #include "llvm/Support/LEB128.h"
-#include "llvm/Support/SystemZ/zOSSupport.h"
 
 #include <string.h> // for memcpy
 

@perry-ca perry-ca requested review from fmayer and redstar November 12, 2025 15:34
@perry-ca perry-ca self-assigned this Nov 12, 2025
@github-actions
Copy link

github-actions bot commented Nov 12, 2025

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

@perry-ca perry-ca requested a review from tltao November 12, 2025 15:48
Copy link
Contributor

@abhina-sree abhina-sree left a comment

Choose a reason for hiding this comment

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

LGTM after fixing the formatting issue

Copy link
Contributor

@zibi2 zibi2 left a comment

Choose a reason for hiding this comment

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

LGTM

@perry-ca perry-ca changed the title Provide a more seamless way to provide missing functions on z/OS Implement a more seamless way to provide missing functions on z/OS Nov 12, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

clang:bytecode Issues for the clang bytecode constexpr interpreter clang:frontend Language frontend issues, e.g. anything involving "Sema" clang Clang issues not falling into any other category llvm:binary-utilities llvm:support objectyaml tools:llvm-exegesis

Projects

None yet

Development

Successfully merging this pull request may close these issues.

6 participants