]> git.ipfire.org Git - thirdparty/curl.git/commitdiff
socketpair: support pipe2 where available
authorAndy Pan <i@andypan.me>
Sun, 6 Apr 2025 12:37:10 +0000 (20:37 +0800)
committerDaniel Stenberg <daniel@haxx.se>
Mon, 7 Apr 2025 10:35:17 +0000 (12:35 +0200)
By replacing pipe with pipe2, it would save us 4 extra system calls of
setting O_NONBLOCK and O_CLOEXEC. This system call is widely supported
across UNIX-like OS's: Linux, *BSD, and SunOS derivatives - Solaris,
illumos, etc.

Ref:
https://man7.org/linux/man-pages/man2/pipe.2.html
https://man.freebsd.org/cgi/man.cgi?query=pipe
https://man.dragonflybsd.org/?command=pipe2
https://man.netbsd.org/pipe.2
https://man.openbsd.org/pipe.2
https://docs.oracle.com/cd/E88353_01/html/E37841/pipe2-2.html
https://illumos.org/man/2/pipe2
https://www.gnu.org/software/gnulib/manual/html_node/pipe2.html

Closes #16987

CMake/unix-cache.cmake
CMake/win32-cache.cmake
CMakeLists.txt
configure.ac
lib/curl_config.h.cmake
lib/socketpair.c

index d97709bcf0b3b8cecf17b0119636b961fa4bb3de..58da04e22299c016fa1dc1e51f5d597808d05f4d 100644 (file)
@@ -192,6 +192,15 @@ set(HAVE_NETINET_UDP_H 1)
 set(HAVE_NET_IF_H 1)
 set(HAVE_OPENDIR 1)
 set(HAVE_PIPE 1)
+if(APPLE OR
+   CYGWIN)
+  set(HAVE_PIPE2 0)
+elseif(CMAKE_SYSTEM_NAME STREQUAL "Linux" OR
+       CMAKE_SYSTEM_NAME STREQUAL "FreeBSD" OR
+       CMAKE_SYSTEM_NAME STREQUAL "NetBSD" OR
+       CMAKE_SYSTEM_NAME STREQUAL "OpenBSD")
+  set(HAVE_PIPE2 1)
+endif()
 set(HAVE_POLL 1)
 set(HAVE_POLL_H 1)
 if(CMAKE_SYSTEM_NAME STREQUAL "Linux")
index aac0678e75a802b989a9b88b9c832fa376e6b73f..5bf8f203fb31f07d6670ed260a5ae0ed5cd51b39 100644 (file)
@@ -139,6 +139,7 @@ set(HAVE_NETINET_TCP_H 0)
 set(HAVE_NETINET_UDP_H 0)
 set(HAVE_NET_IF_H 0)
 set(HAVE_PIPE 0)
+set(HAVE_PIPE2 0)
 set(HAVE_POLL 0)
 set(HAVE_POLL_H 0)
 set(HAVE_POSIX_STRERROR_R 0)
index 38c7847a32788ccbec094a076cd7bb4b8f975457..7edaf518b86188336009e8e9cf72697be7a25ab9 100644 (file)
@@ -281,7 +281,7 @@ endif()
 
 include(PickyWarnings)
 
-if(CMAKE_SYSTEM_NAME STREQUAL "Linux")
+if(CYGWIN OR CMAKE_SYSTEM_NAME STREQUAL "Linux")
   string(APPEND CMAKE_C_FLAGS " -D_GNU_SOURCE")  # Required for sendmmsg() and accept4()
 endif()
 
@@ -1772,6 +1772,7 @@ check_symbol_exists("getaddrinfo"     "${CURL_INCLUDES};stdlib.h;string.h" HAVE_
 check_symbol_exists("getifaddrs"      "${CURL_INCLUDES};stdlib.h" HAVE_GETIFADDRS)  # ifaddrs.h
 check_symbol_exists("freeaddrinfo"    "${CURL_INCLUDES}" HAVE_FREEADDRINFO)  # ws2tcpip.h sys/socket.h netdb.h
 check_function_exists("pipe"          HAVE_PIPE)
+check_function_exists("pipe2"         HAVE_PIPE2)
 check_function_exists("eventfd"       HAVE_EVENTFD)
 check_symbol_exists("ftruncate"       "unistd.h" HAVE_FTRUNCATE)
 check_symbol_exists("getpeername"     "${CURL_INCLUDES}" HAVE_GETPEERNAME)  # winsock2.h unistd.h proto/bsdsocket.h
index fde12e559f89f6a809ebe1bde188206f1a0e8988..f99548e290658eb6ebbe93f83055b3c928ddc2cf 100644 (file)
@@ -577,7 +577,7 @@ AM_CONDITIONAL(BUILD_UNITTESTS, test x$supports_unittests = xyes)
 # In order to detect support of sendmmsg() and accept4(), we need to escape the POSIX
 # jail by defining _GNU_SOURCE or <sys/socket.h> will not expose it.
 case $host_os in
-  linux*)
+  linux*|cygwin*|msys*)
     CPPFLAGS="$CPPFLAGS -D_GNU_SOURCE"
     ;;
 esac
@@ -4124,6 +4124,7 @@ AC_CHECK_FUNCS([\
   gettimeofday \
   mach_absolute_time \
   pipe \
+  pipe2 \
   poll \
   sendmmsg \
   sendmsg \
index 12d513cce995754d12db378606fa39af3064946d..90f7d5145912ec6b462fe14ae4ccf713129f987f 100644 (file)
 /* Define to 1 if you have the `pipe' function. */
 #cmakedefine HAVE_PIPE 1
 
+/* Define to 1 if you have the `pipe2' function. */
+#cmakedefine HAVE_PIPE2 1
+
 /* Define to 1 if you have the `eventfd' function. */
 #cmakedefine HAVE_EVENTFD 1
 
index e4ca2cffa03b9031a8ba27532939b6bc1b9156c3..cfca37bf131f89979e6f54146a3471fd67e23182 100644 (file)
@@ -50,6 +50,11 @@ int Curl_eventfd(curl_socket_t socks[2], bool nonblocking)
 
 int Curl_pipe(curl_socket_t socks[2], bool nonblocking)
 {
+#ifdef HAVE_PIPE2
+  int flags = nonblocking ? O_NONBLOCK | O_CLOEXEC : O_CLOEXEC;
+  if(pipe2(socks, flags))
+    return -1;
+#else
   if(pipe(socks))
     return -1;
 #ifdef HAVE_FCNTL
@@ -70,6 +75,7 @@ int Curl_pipe(curl_socket_t socks[2], bool nonblocking)
       return -1;
     }
   }
+#endif
 
   return 0;
 }