diff -u -r -N libuv--orig/Makefile.am libuv-/Makefile.am --- libuv--orig/Makefile.am 2020-04-19 17:15:57.000000000 +0000 +++ libuv-/Makefile.am 2020-05-12 16:53:56.813839640 +0000 @@ -131,7 +131,7 @@ TESTS = test/run-tests check_PROGRAMS = test/run-tests -test_run_tests_CFLAGS = +test_run_tests_CFLAGS = @CFLAGS@ if SUNOS # Can't be turned into a CC_CHECK_CFLAGS in configure.ac, it makes compilers @@ -327,6 +327,11 @@ test_run_tests_CFLAGS += -D_BSD_SOURCE endif +if IRIX +test_run_tests_CFLAGS += -D_SGI_SOURCE -D_SGI_REENTRANT_FUNCTIONS +#test_run_tests_LDFLAGS += -lutil +endif + if LINUX test_run_tests_CFLAGS += -D_GNU_SOURCE endif @@ -456,6 +461,14 @@ src/unix/posix-hrtime.c \ src/unix/posix-poll.c endif + +if IRIX +uvinclude_HEADERS += include/uv/posix.h +libuv_la_SOURCES += src/unix/irix-common.c \ + src/unix/no-fsevents.c \ + src/unix/posix-hrtime.c \ + src/unix/posix-poll.c +endif if LINUX uvinclude_HEADERS += include/uv/linux.h diff -u -r -N libuv--orig/configure.ac libuv-/configure.ac --- libuv--orig/configure.ac 2020-04-19 17:15:57.000000000 +0000 +++ libuv-/configure.ac 2020-05-12 16:53:56.815012040 +0000 @@ -56,6 +56,7 @@ AM_CONDITIONAL([FREEBSD], [AS_CASE([$host_os],[*freebsd*], [true], [false])]) AM_CONDITIONAL([HAIKU], [AS_CASE([$host_os],[haiku], [true], [false])]) AM_CONDITIONAL([HURD], [AS_CASE([$host_os],[gnu*], [true], [false])]) +AM_CONDITIONAL([IRIX], [AS_CASE([$host_os],[irix*], [true], [false])]) AM_CONDITIONAL([LINUX], [AS_CASE([$host_os],[linux*], [true], [false])]) AM_CONDITIONAL([MSYS], [AS_CASE([$host_os],[msys*], [true], [false])]) AM_CONDITIONAL([NETBSD], [AS_CASE([$host_os],[netbsd*], [true], [false])]) diff -u -r -N libuv--orig/include/uv/unix.h libuv-/include/uv/unix.h --- libuv--orig/include/uv/unix.h 2020-04-19 17:15:57.000000000 +0000 +++ libuv-/include/uv/unix.h 2020-05-12 16:53:56.816759240 +0000 @@ -67,6 +67,8 @@ defined(__MSYS__) || \ defined(__GNU__) # include "uv/posix.h" +#elif defined(__sgi) +# include "uv/posix.h" #elif defined(__HAIKU__) # include "uv/posix.h" #endif diff -u -r -N libuv--orig/src/unix/core.c libuv-/src/unix/core.c --- libuv--orig/src/unix/core.c 2020-04-19 17:15:57.000000000 +0000 +++ libuv-/src/unix/core.c 2020-05-12 16:53:56.819867000 +0000 @@ -18,6 +18,29 @@ * IN THE SOFTWARE. */ +#if defined(__sgi) + +# define SCM_RIGHTS 0x01 + +# include +# include +# include +# include +# include +/* Ugly redefines to use xpg5 style recvmsg/sendmsg and msg_flags */ +/* (Since we can't just define _XOPEN_SOURCE 500 without breaking other stuff */ +# undef CMSG_FIRSTHDR +# define CMSG_FIRSTHDR(mhdr) ((struct cmsghdr *)(mhdr)->msg_ctrl) +# undef CMSG_NXTHDR +# define CMSG_NXTHDR(mhdr, cmsg) \ + (((caddr_t)(cmsg) + (cmsg)->cmsg_len + sizeof(struct cmsghdr) > \ + (caddr_t)(mhdr)->msg_ctrl + (mhdr)->msg_ctrllen) ? \ + (struct cmsghdr *)0L : \ + (struct cmsghdr *)((caddr_t)(cmsg) + _ALIGN((cmsg)->cmsg_len))) +extern ssize_t _xpg5_recvmsg(int, struct xpg5_msghdr *, int); +extern ssize_t _xpg5_sendmsg(int, const struct xpg5_msghdr *, int); +#endif + #include "uv.h" #include "internal.h" @@ -577,7 +600,7 @@ } -#if !defined(__CYGWIN__) && !defined(__MSYS__) && !defined(__HAIKU__) +#if !defined(__CYGWIN__) && !defined(__MSYS__) && !defined(__HAIKU__) && !defined(__sgi) int uv__cloexec_ioctl(int fd, int set) { int r; @@ -655,7 +678,11 @@ } +#if defined(__sgi) +ssize_t uv__recvmsg(int fd, struct xpg5_msghdr* msg, int flags) { +#else ssize_t uv__recvmsg(int fd, struct msghdr* msg, int flags) { +#endif struct cmsghdr* cmsg; ssize_t rc; int* pfd; @@ -675,12 +702,18 @@ } else { rc = recvmsg(fd, msg, flags); } +#elif defined(__sgi) + rc = _xpg5_recvmsg(fd, msg, flags); #else rc = recvmsg(fd, msg, flags); #endif if (rc == -1) return UV__ERR(errno); +#if defined(__sgi) + if (msg->msg_ctrllen == 0) +#else if (msg->msg_controllen == 0) +#endif return rc; for (cmsg = CMSG_FIRSTHDR(msg); cmsg != NULL; cmsg = CMSG_NXTHDR(msg, cmsg)) if (cmsg->cmsg_type == SCM_RIGHTS) diff -u -r -N libuv--orig/src/unix/fs.c libuv-/src/unix/fs.c --- libuv--orig/src/unix/fs.c 2020-04-19 17:15:57.000000000 +0000 +++ libuv-/src/unix/fs.c 2020-05-12 16:55:11.502453840 +0000 @@ -504,7 +504,7 @@ } -#if defined(__APPLE__) && !defined(MAC_OS_X_VERSION_10_8) +#if (defined(__APPLE__) || defined(__sgi)) && !defined(MAC_OS_X_VERSION_10_8) #define UV_CONST_DIRENT uv__dirent_t #else #define UV_CONST_DIRENT const uv__dirent_t @@ -633,6 +633,10 @@ struct statvfs buf; if (0 != statvfs(req->path, &buf)) +#elif defined(__sgi) + struct statfs buf; + + if (0 != statfs(req->path, &buf, sizeof(struct statfs), 0)) #else struct statfs buf; @@ -648,13 +652,20 @@ #if defined(__sun) || defined(__MVS__) || defined(__OpenBSD__) || defined(__NetBSD__) || defined(__HAIKU__) stat_fs->f_type = 0; /* f_type is not supported. */ +#elif defined(__sgi) + stat_fs->f_type = buf.f_fstyp; #else stat_fs->f_type = buf.f_type; #endif stat_fs->f_bsize = buf.f_bsize; stat_fs->f_blocks = buf.f_blocks; stat_fs->f_bfree = buf.f_bfree; + /* Hack, irix doesn't have free blocks available, so set it to total free */ +#if defined(__sgi) + stat_fs->f_bavail = buf.f_bfree; +#else stat_fs->f_bavail = buf.f_bavail; +#endif stat_fs->f_files = buf.f_files; stat_fs->f_ffree = buf.f_ffree; req->ptr = stat_fs; @@ -741,8 +752,12 @@ #else ssize_t len; +#if defined(__sgi) + buf = uv__malloc(PATH_MAX + 1); +#else len = uv__fs_pathmax_size(req->path); buf = uv__malloc(len + 1); +#endif if (buf == NULL) { errno = ENOMEM; diff -u -r -N libuv--orig/src/unix/internal.h libuv-/src/unix/internal.h --- libuv--orig/src/unix/internal.h 2020-04-19 17:15:57.000000000 +0000 +++ libuv-/src/unix/internal.h 2020-05-12 16:53:56.825402440 +0000 @@ -195,7 +195,11 @@ int uv__close_nocheckstdio(int fd); int uv__close_nocancel(int fd); int uv__socket(int domain, int type, int protocol); +#if defined(__sgi) +ssize_t uv__recvmsg(int fd, struct xpg5_msghdr *msg, int flags); +#else ssize_t uv__recvmsg(int fd, struct msghdr *msg, int flags); +#endif void uv__make_close_pending(uv_handle_t* handle); int uv__getiovmax(void); @@ -323,10 +327,17 @@ typedef int (*uv__peersockfunc)(int, struct sockaddr*, socklen_t*); +#if defined(__sgi) +int uv__getsockpeername(const uv_handle_t* handle, + uv__peersockfunc func, + struct sockaddr* name, + socklen_t* namelen); +#else int uv__getsockpeername(const uv_handle_t* handle, uv__peersockfunc func, struct sockaddr* name, int* namelen); +#endif #if defined(__linux__) || \ defined(__FreeBSD__) || \ diff -u -r -N libuv--orig/src/unix/irix-common.c libuv-/src/unix/irix-common.c --- libuv--orig/src/unix/irix-common.c 1970-01-01 00:00:00.000000000 +0000 +++ libuv-/src/unix/irix-common.c 2020-05-12 16:53:56.827414840 +0000 @@ -0,0 +1,462 @@ +/* Copyright libuv project contributors. All rights reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to + * deal in the Software without restriction, including without limitation the + * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or + * sell copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS + * IN THE SOFTWARE. + */ + +#include "uv.h" +#include "internal.h" + +#include +#include +#include +#include +#include +#include + +#include +#include +#include +#include +#include +#include +#include +#include + +#include + +#include +#include +#include +#include +#include + +#include + +#if defined(__sgi) +# include +#endif + +static uv_mutex_t process_title_mutex; +static uv_once_t process_title_mutex_once = UV_ONCE_INIT; +static void* args_mem = NULL; +static char** process_argv = NULL; +static int process_argc = 0; +static char* process_title_ptr = NULL; + +int uv_resident_set_memory(size_t* rss) { + + pid_t pid = getpid(); + int fd; + + char procname[BUFSIZ]; + + sprintf(procname, "/proc/%ld", pid); + + if( (fd = open(procname, O_RDONLY)) < 0 ) { + return UV__ERR(errno); + } + + struct prpsinfo psinfo; + + if( ioctl(fd, PIOCPSINFO, &psinfo) < 0 ) { + close(fd); + return UV__ERR(errno); + } + + long size_from_ps = psinfo.pr_rssize; + + close(fd); + + *rss = size_from_ps; + + return 0; +} + +uint64_t uv_get_free_memory(void) { + struct rminfo realmem; + long pagesize; + if (sysmp(MP_SAGET, MPSA_RMINFO, &realmem, sizeof(realmem)) == -1) { + return 0; + } + pagesize = sysconf(_SC_PAGESIZE); + return (uint64_t)realmem.freemem * pagesize; +} + + +uint64_t uv_get_total_memory(void) { + struct rminfo realmem; + long pagesize; + if (sysmp(MP_SAGET, MPSA_RMINFO, &realmem, sizeof(realmem)) == -1) { + return 0; + } + pagesize = sysconf(_SC_PAGESIZE); + return (uint64_t)realmem.physmem * pagesize; +} + + +uint64_t uv_get_constrained_memory(void) { + return 0; /* Memory constraints are unknown. */ +} + + +void uv_loadavg(double avg[3]) { + int avenrun[3]; + + sgt_cookie_t cookie; + + int i; + + if (sysmp(MP_KERNADDR, MPKA_AVENRUN) == -1) { + avg[0] = 0.; avg[1] = 0.; avg[2] = 0.; + return; + } + + SGT_COOKIE_INIT(&cookie); + SGT_COOKIE_SET_KSYM(&cookie, "avenrun"); + + if (sysget(SGT_KSYM, (char *)avenrun, sizeof(avenrun), + SGT_READ, &cookie) != sizeof(avenrun)) { + avg[0] = 0.; avg[1] = 0.; avg[2] = 0.; + return; + } + + for (i = 0; i < 3; i++ ) { + avg[i] = avenrun[i]; + avg[i] /= 1024.0; + } +} + +int uv_cpu_info(uv_cpu_info_t** cpu_infos, int* count) { + uv_cpu_info_t *cpu_info; + int ncpus, i = 0; + + ncpus = sysconf(_SC_NPROC_ONLN); + + *cpu_infos = (uv_cpu_info_t*) uv__malloc(ncpus * sizeof(uv_cpu_info_t)); + if (!*cpu_infos) { + return UV_ENOMEM; + } + + cpu_info = *cpu_infos; + while(i < ncpus) { + cpu_info->speed = 100; + cpu_info->model = "CPU"; + cpu_info->cpu_times.user = 0; + cpu_info->cpu_times.sys = 0; + cpu_info->cpu_times.idle = 100; + cpu_info->cpu_times.irq = 0; + cpu_info->cpu_times.nice = 0; + cpu_info++; + i++; + } + return 0; +} + +int uv_uptime(double* uptime) { + struct utmp *utmp_buf; + size_t entries = 0; + time_t boot_time; + + boot_time = 0; + utmpname(UTMP_FILE); + + setutent(); + + while ((utmp_buf = getutent()) != NULL) { + if (utmp_buf->ut_user[0] && utmp_buf->ut_type == USER_PROCESS) + ++entries; + if (utmp_buf->ut_type == BOOT_TIME) + boot_time = utmp_buf->ut_time; + } + + endutent(); + + if (boot_time == 0) + return UV_ENOSYS; + + *uptime = time(NULL) - boot_time; + return 0; +} + + +int uv_exepath(char* buffer, size_t* size) { + char filename[50]; + char abspath[PATH_MAX]; + char firstarg[PATH_MAX]; + size_t abspath_size; + int fd; + + if (buffer == NULL || size == NULL || *size == 0) + return UV_EINVAL; + + sprintf (filename, "/proc/pinfo/%d", (int) getpid ()); + fd = open (filename, O_RDONLY); + if (0 <= fd) { + prpsinfo_t buf; + int ioctl_ok = 0 <= ioctl (fd, PIOCPSINFO, &buf); + close (fd); + if (ioctl_ok) + { + int offset = strchr(buf.pr_psargs, ' ') - buf.pr_psargs; + memcpy(firstarg, buf.pr_psargs, offset); + firstarg[offset] = '\0'; + + printf("%s\n", firstarg); + + if(!realpath(firstarg, abspath)) + return UV__ERR(errno); + + abspath_size = strlen(abspath); + + *size -= 1; + if (*size > abspath_size) + *size = abspath_size; + + memcpy(buffer, abspath, *size); + buffer[*size] = '\0'; + + return 0; + } + } + return UV__EINVAL; +} + +static void init_process_title_mutex_once(void) { + uv_mutex_init(&process_title_mutex); +} + +char** uv_setup_args(int argc, char** argv) { + char** new_argv; + size_t size; + char* s; + int i; + + if (argc <= 0) + return argv; + + /* Save the original pointer to argv. + * AIX uses argv to read the process name. + * (Not the memory pointed to by argv[0..n] as on Linux.) + */ + process_argv = argv; + process_argc = argc; + + /* Calculate how much memory we need for the argv strings. */ + size = 0; + for (i = 0; i < argc; i++) + size += strlen(argv[i]) + 1; + + /* Add space for the argv pointers. */ + size += (argc + 1) * sizeof(char*); + + new_argv = uv__malloc(size); + if (new_argv == NULL) + return argv; + args_mem = new_argv; + + /* Copy over the strings and set up the pointer table. */ + s = (char*) &new_argv[argc + 1]; + for (i = 0; i < argc; i++) { + size = strlen(argv[i]) + 1; + memcpy(s, argv[i], size); + new_argv[i] = s; + s += size; + } + new_argv[i] = NULL; + + return new_argv; +} + +int uv_set_process_title(const char* title) { + char* new_title; + + /* We cannot free this pointer when libuv shuts down, + * the process may still be using it. + */ + new_title = uv__strdup(title); + if (new_title == NULL) + return UV_ENOMEM; + + uv_once(&process_title_mutex_once, init_process_title_mutex_once); + uv_mutex_lock(&process_title_mutex); + + /* If this is the first time this is set, + * don't free and set argv[1] to NULL. + */ + if (process_title_ptr != NULL) + uv__free(process_title_ptr); + + process_title_ptr = new_title; + + process_argv[0] = process_title_ptr; + if (process_argc > 1) + process_argv[1] = NULL; + + uv_mutex_unlock(&process_title_mutex); + + return 0; +} + +int uv_get_process_title(char* buffer, size_t size) { + size_t len; + if (buffer == NULL || size == 0) + return UV_EINVAL; + + uv_once(&process_title_mutex_once, init_process_title_mutex_once); + uv_mutex_lock(&process_title_mutex); + + len = strlen(process_argv[0]); + if (size <= len) { + uv_mutex_unlock(&process_title_mutex); + return UV_ENOBUFS; + } + + memcpy(buffer, process_argv[0], len); + buffer[len] = '\0'; + + uv_mutex_unlock(&process_title_mutex); + + return 0; +} + +int uv_interface_addresses(uv_interface_address_t** addresses, int* count) { + uv_interface_address_t* address; + int sockfd, inet6; + struct ifconf ifc; + + *count = 0; + *addresses = NULL; + + if (0 > (sockfd = socket(AF_INET, SOCK_DGRAM, IPPROTO_IP))) { + return UV__ERR(errno); + } + + char buf[BUFSIZ]; + + ifc.ifc_len = sizeof(buf); + ifc.ifc_buf = buf; + if (ioctl(sockfd, SIOCGIFCONF, &ifc) == -1) { + uv__close(sockfd); + return UV__ERR(errno); + } + + /*#define ADDR_SIZE(p) MAX((p).sa_len, sizeof(p))*/ +#define ADDR_SIZE(p) sizeof(p) + + /* Count all up and running ipv4/ipv6 addresses */ + struct ifreq *ifr, *p, flg; + struct sockaddr_dl* sa_addr; + ifr = ifc.ifc_req; + while ((char*)ifr < (char*)ifc.ifc_req + ifc.ifc_len) { + p = ifr; + ifr = (struct ifreq*) + ((char*)ifr + sizeof(ifr->ifr_name) + ADDR_SIZE(ifr->ifr_addr)); + + if (!(p->ifr_addr.sa_family == AF_INET6 || + p->ifr_addr.sa_family == AF_INET)) + continue; + + memcpy(flg.ifr_name, p->ifr_name, sizeof(flg.ifr_name)); + if (ioctl(sockfd, SIOCGIFFLAGS, &flg) == -1) { + uv__close(sockfd); + return UV__ERR(errno); + } + + if (!(flg.ifr_flags & IFF_UP && flg.ifr_flags & IFF_RUNNING)) + continue; + + (*count)++; + } + + if (*count == 0) { + uv__close(sockfd); + return 0; + } + + /* Alloc the return interface structs */ + *addresses = uv__malloc(*count * sizeof(uv_interface_address_t)); + if (!(*addresses)) { + uv__close(sockfd); + return UV_ENOMEM; + } + address = *addresses; + + ifr = ifc.ifc_req; + while ((char*)ifr < (char*)ifc.ifc_req + ifc.ifc_len) { + p = ifr; + ifr = (struct ifreq*) + ((char*)ifr + sizeof(ifr->ifr_name) + ADDR_SIZE(ifr->ifr_addr)); + + if (!(p->ifr_addr.sa_family == AF_INET6 || + p->ifr_addr.sa_family == AF_INET)) + continue; + + inet6 = (p->ifr_addr.sa_family == AF_INET6); + + memcpy(flg.ifr_name, p->ifr_name, sizeof(flg.ifr_name)); + if (ioctl(sockfd, SIOCGIFFLAGS, &flg) == -1) { + uv__close(sockfd); + return UV_ENOSYS; + } + + if (!(flg.ifr_flags & IFF_UP && flg.ifr_flags & IFF_RUNNING)) + continue; + + /* All conditions above must match count loop */ + + address->name = uv__strdup(p->ifr_name); + + if (inet6) + address->address.address6 = *((struct sockaddr_in6*) &p->ifr_addr); + else + address->address.address4 = *((struct sockaddr_in*) &p->ifr_addr); + + sa_addr = (struct sockaddr_dl*) &p->ifr_addr; + memcpy(address->phys_addr, sa_addr, sizeof(address->phys_addr)); + + if (ioctl(sockfd, SIOCGIFNETMASK, p) == -1) { + uv__close(sockfd); + return UV_ENOSYS; + } + + if (inet6) + address->netmask.netmask6 = *((struct sockaddr_in6*) &p->ifr_addr); + else + address->netmask.netmask4 = *((struct sockaddr_in*) &p->ifr_addr); + + address->is_internal = flg.ifr_flags & IFF_LOOPBACK ? 1 : 0; + + address++; + } + + uv__close(sockfd); + return 0; +} + + +void uv_free_interface_addresses(uv_interface_address_t* addresses, + int count) { + int i; + + for (i = 0; i < count; ++i) { + uv__free(addresses[i].name); + } + + uv__free(addresses); +} diff -u -r -N libuv--orig/src/unix/posix-hrtime.c libuv-/src/unix/posix-hrtime.c --- libuv--orig/src/unix/posix-hrtime.c 2020-04-19 17:15:57.000000000 +0000 +++ libuv-/src/unix/posix-hrtime.c 2020-05-12 16:53:56.828877000 +0000 @@ -30,6 +30,10 @@ uint64_t uv__hrtime(uv_clocktype_t type) { struct timespec ts; +#if defined(__sgi) + clock_gettime(CLOCK_SGI_CYCLE, &ts); +#else clock_gettime(CLOCK_MONOTONIC, &ts); +#endif return (((uint64_t) ts.tv_sec) * NANOSEC + ts.tv_nsec); } diff -u -r -N libuv--orig/src/unix/stream.c libuv-/src/unix/stream.c --- libuv--orig/src/unix/stream.c 2020-04-19 17:15:57.000000000 +0000 +++ libuv-/src/unix/stream.c 2020-05-12 16:53:56.832219800 +0000 @@ -19,6 +19,29 @@ * IN THE SOFTWARE. */ +#if defined(__sgi) + +# define SCM_RIGHTS 0x01 + +# include +# include +# include +# include +# include +/* Ugly redefines to use xpg5 style recvmsg/sendmsg and msg_flags */ +/* (Since we can't just define _XOPEN_SOURCE 500 without breaking other stuff */ +# undef CMSG_FIRSTHDR +# define CMSG_FIRSTHDR(mhdr) ((struct cmsghdr *)(mhdr)->msg_ctrl) +# undef CMSG_NXTHDR +# define CMSG_NXTHDR(mhdr, cmsg) \ + (((caddr_t)(cmsg) + (cmsg)->cmsg_len + sizeof(struct cmsghdr) > \ + (caddr_t)(mhdr)->msg_ctrl + (mhdr)->msg_ctrllen) ? \ + (struct cmsghdr *)0L : \ + (struct cmsghdr *)((caddr_t)(cmsg) + _ALIGN((cmsg)->cmsg_len))) +extern ssize_t _xpg5_recvmsg(int, struct xpg5_msghdr *, int); +extern ssize_t _xpg5_sendmsg(int, const struct xpg5_msghdr *, int); +#endif + #include "uv.h" #include "internal.h" @@ -840,7 +863,11 @@ if (req->send_handle) { int fd_to_send; +#if defined(__sgi) + struct xpg5_msghdr msg; +#else struct msghdr msg; +#endif struct cmsghdr *cmsg; union { char data[64]; @@ -864,8 +891,13 @@ msg.msg_iovlen = iovcnt; msg.msg_flags = 0; +#if defined(__sgi) + msg.msg_ctrl = &scratch.alias; + msg.msg_ctrllen = CMSG_SPACE(sizeof(fd_to_send)); +#else msg.msg_control = &scratch.alias; msg.msg_controllen = CMSG_SPACE(sizeof(fd_to_send)); +#endif cmsg = CMSG_FIRSTHDR(&msg); cmsg->cmsg_level = SOL_SOCKET; @@ -880,7 +912,11 @@ } do +#if defined(__sgi) + n = _xpg5_sendmsg(uv__stream_fd(stream), &msg, 0); +#else n = sendmsg(uv__stream_fd(stream), &msg, 0); +#endif while (n == -1 && RETRY_ON_WRITE_ERROR(errno)); /* Ensure the handle isn't sent again in case this is a partial write. */ @@ -1057,7 +1093,11 @@ #define UV__CMSG_FD_SIZE (UV__CMSG_FD_COUNT * sizeof(int)) +#if defined(__sgi) +static int uv__stream_recv_cmsg(uv_stream_t* stream, struct xpg5_msghdr* msg) { +#else static int uv__stream_recv_cmsg(uv_stream_t* stream, struct msghdr* msg) { +#endif struct cmsghdr* cmsg; for (cmsg = CMSG_FIRSTHDR(msg); cmsg != NULL; cmsg = CMSG_NXTHDR(msg, cmsg)) { @@ -1116,7 +1156,11 @@ static void uv__read(uv_stream_t* stream) { uv_buf_t buf; ssize_t nread; +#if defined(__sgi) + struct xpg5_msghdr msg; +#else struct msghdr msg; +#endif char cmsg_space[CMSG_SPACE(UV__CMSG_FD_SIZE)]; int count; int err; @@ -1163,8 +1207,13 @@ msg.msg_name = NULL; msg.msg_namelen = 0; /* Set up to receive a descriptor even if one isn't in the message */ +#if defined(__sgi) + msg.msg_ctrllen = sizeof(cmsg_space); + msg.msg_ctrl = cmsg_space; +#else msg.msg_controllen = sizeof(cmsg_space); msg.msg_control = cmsg_space; +#endif do { nread = uv__recvmsg(uv__stream_fd(stream), &msg, 0); diff -u -r -N libuv--orig/src/unix/thread.c libuv-/src/unix/thread.c --- libuv--orig/src/unix/thread.c 2020-04-19 17:15:57.000000000 +0000 +++ libuv-/src/unix/thread.c 2020-05-12 16:55:17.456901120 +0000 @@ -241,6 +241,8 @@ #ifdef PTHREAD_STACK_MIN if (stack_size < PTHREAD_STACK_MIN) stack_size = PTHREAD_STACK_MIN; +#else +# error "Missing PTHREAD_STACK_MIN" #endif } @@ -708,7 +710,7 @@ if (err) return UV__ERR(err); -#if !(defined(__ANDROID_API__) && __ANDROID_API__ < 21) +#if !(defined(__ANDROID_API__) && __ANDROID_API__ < 21) && !defined(__sgi) err = pthread_condattr_setclock(&attr, CLOCK_MONOTONIC); if (err) goto error2; @@ -786,7 +788,7 @@ int uv_cond_timedwait(uv_cond_t* cond, uv_mutex_t* mutex, uint64_t timeout) { int r; struct timespec ts; -#if defined(__MVS__) +#if defined(__MVS__) || defined(__sgi) struct timeval tv; #endif @@ -795,7 +797,7 @@ ts.tv_nsec = timeout % NANOSEC; r = pthread_cond_timedwait_relative_np(cond, mutex, &ts); #else -#if defined(__MVS__) +#if defined(__MVS__) || defined(__sgi) if (gettimeofday(&tv, NULL)) abort(); timeout += tv.tv_sec * NANOSEC + tv.tv_usec * 1e3; diff -u -r -N libuv--orig/src/unix/tty.c libuv-/src/unix/tty.c --- libuv--orig/src/unix/tty.c 2020-04-19 17:15:57.000000000 +0000 +++ libuv-/src/unix/tty.c 2020-05-12 16:55:02.256048160 +0000 @@ -231,7 +231,7 @@ static void uv__tty_make_raw(struct termios* tio) { assert(tio != NULL); -#if defined __sun || defined __MVS__ +#if defined __sun || defined __MVS__ || defined(__sgi) /* * This implementation of cfmakeraw for Solaris and derivatives is taken from * http://www.perkin.org.uk/posts/solaris-portability-cfmakeraw.html. @@ -352,7 +352,7 @@ return UV_UDP; if (type == SOCK_STREAM) { -#if defined(_AIX) || defined(__DragonFly__) +#if defined(_AIX) || defined(__DragonFly__) || defined(__sgi) /* on AIX/DragonFly the getsockname call returns an empty sa structure * for sockets of type AF_UNIX. For all other types it will * return a properly filled in structure. diff -u -r -N libuv--orig/src/unix/udp.c libuv-/src/unix/udp.c --- libuv--orig/src/unix/udp.c 2020-04-19 17:15:57.000000000 +0000 +++ libuv-/src/unix/udp.c 2020-05-12 16:53:56.839168440 +0000 @@ -19,6 +19,29 @@ * IN THE SOFTWARE. */ +#if defined(__sgi) + +# define SCM_RIGHTS 0x01 + +# include +# include +# include +# include +# include +/* Ugly redefines to use xpg5 style recvmsg/sendmsg and msg_flags */ +/* (Since we can't just define _XOPEN_SOURCE 500 without breaking other stuff */ +# undef CMSG_FIRSTHDR +# define CMSG_FIRSTHDR(mhdr) ((struct cmsghdr *)(mhdr)->msg_ctrl) +# undef CMSG_NXTHDR +# define CMSG_NXTHDR(mhdr, cmsg) \ + (((caddr_t)(cmsg) + (cmsg)->cmsg_len + sizeof(struct cmsghdr) > \ + (caddr_t)(mhdr)->msg_ctrl + (mhdr)->msg_ctrllen) ? \ + (struct cmsghdr *)0L : \ + (struct cmsghdr *)((caddr_t)(cmsg) + _ALIGN((cmsg)->cmsg_len))) +extern ssize_t _xpg5_recvmsg(int, struct xpg5_msghdr *, int); +extern ssize_t _xpg5_sendmsg(int, const struct xpg5_msghdr *, int); +#endif + #include "uv.h" #include "internal.h" @@ -238,7 +261,11 @@ static void uv__udp_recvmsg(uv_udp_t* handle) { struct sockaddr_storage peer; +#if defined(__sgi) + struct xpg5_msghdr h; +#else struct msghdr h; +#endif ssize_t nread; uv_buf_t buf; int flags; @@ -281,7 +308,11 @@ h.msg_iovlen = 1; do { +#if defined(__sgi) + nread = _xpg5_recvmsg(handle->io_watcher.fd, &h, 0); +#else nread = recvmsg(handle->io_watcher.fd, &h, 0); +#endif } while (nread == -1 && errno == EINTR); @@ -400,7 +431,11 @@ static void uv__udp_sendmsg(uv_udp_t* handle) { uv_udp_send_t* req; +#if defined(__sgi) + struct xpg5_msghdr h; +#else struct msghdr h; +#endif QUEUE* q; ssize_t size; @@ -440,7 +475,11 @@ h.msg_iovlen = req->nbufs; do { +#if defined(__sgi) + size = _xpg5_sendmsg(handle->io_watcher.fd, &h, 0); +#else size = sendmsg(handle->io_watcher.fd, &h, 0); +#endif } while (size == -1 && errno == EINTR); if (size == -1) { @@ -850,7 +889,7 @@ } -#if !defined(__OpenBSD__) && !defined(__NetBSD__) && !defined(__ANDROID__) +#if !defined(__OpenBSD__) && !defined(__NetBSD__) && !defined(__ANDROID__) && !defined(__sgi) static int uv__udp_set_source_membership4(uv_udp_t* handle, const struct sockaddr_in* multicast_addr, const char* interface_addr, @@ -1045,7 +1084,7 @@ const char* interface_addr, const char* source_addr, uv_membership membership) { -#if !defined(__OpenBSD__) && !defined(__NetBSD__) && !defined(__ANDROID__) +#if !defined(__OpenBSD__) && !defined(__NetBSD__) && !defined(__ANDROID__) && !defined(__sgi) int err; struct sockaddr_storage mcast_addr; struct sockaddr_in* mcast_addr4; diff -u -r -N libuv--orig/test/test-ipc.c libuv-/test/test-ipc.c --- libuv--orig/test/test-ipc.c 2020-04-19 17:15:57.000000000 +0000 +++ libuv-/test/test-ipc.c 2020-05-12 16:53:56.841950040 +0000 @@ -19,6 +19,10 @@ * IN THE SOFTWARE. */ +#if defined(__sgi) +# define PRId64 "lld" +#endif + #include "uv.h" #include "task.h" diff -u -r -N libuv--orig/test/test-pipe-sendmsg.c libuv-/test/test-pipe-sendmsg.c --- libuv--orig/test/test-pipe-sendmsg.c 2020-04-19 17:15:57.000000000 +0000 +++ libuv-/test/test-pipe-sendmsg.c 2020-05-12 16:53:56.843942360 +0000 @@ -19,6 +19,29 @@ * IN THE SOFTWARE. */ +#if defined(__sgi) + +# define SCM_RIGHTS 0x01 + +# include +# include +# include +# include +# include +/* Ugly redefines to use xpg5 style recvmsg/sendmsg and msg_flags */ +/* (Since we can't just define _XOPEN_SOURCE 500 without breaking other stuff */ +# undef CMSG_FIRSTHDR +# define CMSG_FIRSTHDR(mhdr) ((struct cmsghdr *)(mhdr)->msg_ctrl) +# undef CMSG_NXTHDR +# define CMSG_NXTHDR(mhdr, cmsg) \ + (((caddr_t)(cmsg) + (cmsg)->cmsg_len + sizeof(struct cmsghdr) > \ + (caddr_t)(mhdr)->msg_ctrl + (mhdr)->msg_ctrllen) ? \ + (struct cmsghdr *)0L : \ + (struct cmsghdr *)((caddr_t)(cmsg) + _ALIGN((cmsg)->cmsg_len))) +extern ssize_t _xpg5_recvmsg(int, struct xpg5_msghdr *, int); +extern ssize_t _xpg5_sendmsg(int, const struct xpg5_msghdr *, int); +#endif + #include "uv.h" #include "task.h" @@ -109,7 +132,11 @@ int r; int fds[2]; int send_fds[ARRAY_SIZE(incoming)]; +#if defined(__sgi) + struct xpg5_msghdr msg; +#else struct msghdr msg; +#endif char scratch[64]; struct cmsghdr *cmsg; unsigned int i; @@ -128,14 +155,24 @@ msg.msg_iovlen = 1; msg.msg_flags = 0; +#if defined(__sgi) + msg.msg_ctrl = (void*) scratch; + msg.msg_ctrllen = CMSG_LEN(sizeof(send_fds)); + ASSERT(sizeof(scratch) >= msg.msg_ctrllen); +#else msg.msg_control = (void*) scratch; msg.msg_controllen = CMSG_LEN(sizeof(send_fds)); ASSERT(sizeof(scratch) >= msg.msg_controllen); +#endif cmsg = CMSG_FIRSTHDR(&msg); cmsg->cmsg_level = SOL_SOCKET; cmsg->cmsg_type = SCM_RIGHTS; +#if defined(__sgi) + cmsg->cmsg_len = msg.msg_ctrllen; +#else cmsg->cmsg_len = msg.msg_controllen; +#endif /* silence aliasing warning */ { @@ -149,7 +186,11 @@ ASSERT(0 == uv_read_start((uv_stream_t*) &p, alloc_cb, read_cb)); do +#if defined(__sgi) + r = _xpg5_sendmsg(fds[0], &msg, 0); +#else r = sendmsg(fds[0], &msg, 0); +#endif while (r == -1 && errno == EINTR); ASSERT(r == 1); diff -u -r -N libuv--orig/test/test-poll.c libuv-/test/test-poll.c --- libuv--orig/test/test-poll.c 2020-04-19 17:15:57.000000000 +0000 +++ libuv-/test/test-poll.c 2020-05-12 16:55:28.413420440 +0000 @@ -622,7 +622,7 @@ #if !defined(__DragonFly__) && !defined(__FreeBSD__) && !defined(__sun) && \ !defined(_AIX) && !defined(__MVS__) && !defined(__FreeBSD_kernel__) && \ !defined(__OpenBSD__) && !defined(__CYGWIN__) && !defined(__MSYS__) && \ - !defined(__NetBSD__) + !defined(__NetBSD__) && !defined(__sgi) uv_poll_t poll_handle; int fd; diff -u -r -N libuv--orig/test/test-process-title-threadsafe.c libuv-/test/test-process-title-threadsafe.c --- libuv--orig/test/test-process-title-threadsafe.c 2020-04-19 17:15:57.000000000 +0000 +++ libuv-/test/test-process-title-threadsafe.c 2020-05-12 16:53:56.845522200 +0000 @@ -19,6 +19,9 @@ * IN THE SOFTWARE. */ +#if defined(__sgi) +# define PRId64 "lld" +#endif #include "uv.h" #include "task.h" diff -u -r -N libuv--orig/test/test-spawn.c libuv-/test/test-spawn.c --- libuv--orig/test/test-spawn.c 2020-04-19 17:15:57.000000000 +0000 +++ libuv-/test/test-spawn.c 2020-05-12 16:53:56.848855480 +0000 @@ -1392,8 +1392,13 @@ ASSERT(pw != NULL); options.uid = pw->pw_uid; options.gid = pw->pw_gid; +#if defined(__sgi) + snprintf(uidstr, sizeof(uidstr), "%ld", pw->pw_uid); + snprintf(gidstr, sizeof(gidstr), "%ld", pw->pw_gid); +#else snprintf(uidstr, sizeof(uidstr), "%d", pw->pw_uid); snprintf(gidstr, sizeof(gidstr), "%d", pw->pw_gid); +#endif options.args[2] = uidstr; options.args[3] = gidstr; options.flags = UV_PROCESS_SETUID | UV_PROCESS_SETGID;