commit aa3d42441d6a7314454191888aeac21682cf2cfe from: Alisdair MacLeod date: Thu Apr 30 19:03:10 2026 UTC Portability: Add shims for timingsafe_bcmp, arc4random_buf, and timegm commit - efaf222244a17c530f5e2150244957d925fbb58a commit + aa3d42441d6a7314454191888aeac21682cf2cfe blob - 5f8e39bd2ff40baa5509001d77ceec8213ab29de blob + 8d7b53e85df424cc4a01c912451f7ed46fecdb6f --- compat.h +++ compat.h @@ -29,6 +29,7 @@ #include #include #include +#include #ifdef __OpenBSD__ #include /* pledge, unveil */ @@ -68,6 +69,71 @@ strsep(char **stringp, const char *delim) #endif /* + * timingsafe_bcmp - constant-time memory comparison. + * Available in OpenBSD and macOS; provide a shim elsewhere. + */ +#if !defined(__OpenBSD__) && !defined(__APPLE__) +static inline int +timingsafe_bcmp(const void *b1, const void *b2, size_t n) +{ + const unsigned char *p1 = b1, *p2 = b2; + int ret = 0; + + for (; n > 0; n--) + ret |= *p1++ ^ *p2++; + return (ret != 0); +} +#endif + +/* + * arc4random_buf - high-quality random bytes. + * Available in OpenBSD and macOS; provide a shim for other platforms. + * For development/testing, reading from /dev/urandom is sufficient. + */ +#if !defined(__OpenBSD__) && !defined(__APPLE__) +#include +#include +static inline void +arc4random_buf(void *buf, size_t n) +{ + int fd = open("/dev/urandom", O_RDONLY); + if (fd == -1) + abort(); + if (read(fd, buf, n) != (ssize_t)n) + abort(); + close(fd); +} +#endif + +/* + * timegm - inverse of gmtime. + * Non-standard but available on many systems; provide a shim for POSIX. + */ +#if !defined(__OpenBSD__) && !defined(__APPLE__) && !defined(__GLIBC__) +static inline time_t +timegm(struct tm *tm) +{ + time_t ret; + char *tz; + + tz = getenv("TZ"); + if (tz != NULL) + tz = strdup(tz); + setenv("TZ", "", 1); + tzset(); + ret = mktime(tm); + if (tz != NULL) { + setenv("TZ", tz, 1); + free(tz); + } else { + unsetenv("TZ"); + } + tzset(); + return ret; +} +#endif + +/* * reallocarray - safe realloc with overflow checking. * Available in OpenBSD and glibc >= 2.26; provide a shim elsewhere * (including macOS/Apple libc which does not provide it).