Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Support OpenBSD #31

Merged
merged 3 commits into from
Feb 25, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 4 additions & 1 deletion Makefile.am
Original file line number Diff line number Diff line change
Expand Up @@ -40,4 +40,7 @@ if INSTALL_FREEBSD_STARTUP
endif
endif


if BUILD_FOR_OPENBSD
# NQPTP starts as root on OpenBSD to access ports 319 and 320
# and drops privileges to the user shairport is running as.
endif
17 changes: 14 additions & 3 deletions configure.ac
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ AC_CANONICAL_HOST

build_linux=no
build_freebsd=no
build_openbsd=no

# Detect the target system
case "${host_os}" in
Expand All @@ -16,7 +17,10 @@ case "${host_os}" in
;;
freebsd*)
build_freebsd=yes
;;
;;
openbsd*)
build_openbsd=yes
;;
*)
AC_MSG_ERROR(["OS $host_os is not supported"])
;;
Expand All @@ -25,13 +29,17 @@ esac
# Pass the conditionals to automake
AM_CONDITIONAL([BUILD_FOR_LINUX], [test "$build_linux" = "yes"])
AM_CONDITIONAL([BUILD_FOR_FREEBSD], [test "$build_freebsd" = "yes"])
AM_CONDITIONAL([BUILD_FOR_OPENBSD], [test "$build_openbsd" = "yes"])

if test "x$build_linux" = "xyes" ; then
AC_DEFINE([CONFIG_FOR_LINUX], 1, [Build for Linux.])
fi
if test "x$build_freebsd" = "xyes" ; then
AC_DEFINE([CONFIG_FOR_FREEBSD], 1, [Build for FreeBSD.])
fi
if test "x$build_openbsd" = "xyes" ; then
AC_DEFINE([CONFIG_FOR_OPENBSD], 1, [Build for OpenBSD.])
fi

AC_CHECK_PROGS([GIT], [git])
if test -n "$GIT" && test -e ".git/index" ; then
Expand All @@ -44,7 +52,7 @@ AM_CONDITIONAL([USE_GIT_VERSION], [test -n "$GIT" && test -e ".git/index" ])
AC_ARG_WITH([systemd-startup],[AS_HELP_STRING([--with-systemd-startup],[install a systemd startup script during a make install])])
AM_CONDITIONAL([INSTALL_SYSTEMD_STARTUP], [test "x$with_systemd_startup" = "xyes"])

# Check to see if we should include the systemd stuff to define it as a service
# Check to see if we should include the FreeBSD stuff to define it as a service
AC_ARG_WITH([freebsd-startup],[AS_HELP_STRING([--with-freebsd-startup],[install a FreeBSD startup script during a make install])])
AM_CONDITIONAL([INSTALL_FREEBSD_STARTUP], [test "x$with_freebsd_startup" = "xyes"])

Expand All @@ -58,7 +66,10 @@ AC_PROG_INSTALL

# Checks for libraries.
AC_CHECK_LIB([pthread],[pthread_create], , AC_MSG_ERROR(pthread library needed))
AC_CHECK_LIB([rt],[clock_gettime], , AC_MSG_ERROR(librt needed for shared memory library))
if test "x$build_openbsd" = "xno" ; then
# part of libc
AC_CHECK_LIB([rt],[clock_gettime], , AC_MSG_ERROR(librt needed for shared memory library))
fi

# Checks for header files.
AC_CHECK_HEADERS([arpa/inet.h inttypes.h netdb.h stdlib.h string.h sys/socket.h unistd.h])
Expand Down
4 changes: 2 additions & 2 deletions nqptp-utilities.c
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@
#include <linux/if_packet.h> // sockaddr_ll
#endif

#ifdef CONFIG_FOR_FREEBSD
#if defined(CONFIG_FOR_FREEBSD) || defined(CONFIG_FOR_OPENBSD)
#include <sys/types.h>
#include <unistd.h>
#include <net/if_dl.h>
Expand Down Expand Up @@ -106,7 +106,7 @@ void open_sockets_at_port(const char *node, uint16_t port,
freeaddrinfo(info);
if (sockets_opened == 0) {
if (errno == EACCES) {
die("nqptp does not have permission to access port %u. It must (a) [Linux only] have been given CAP_NET_BIND_SERVICE capabilities using e.g. setcap or systemd's AmbientCapabilities, or (b) run as root.", port);
die("nqptp does not have permission to access port %u. It must (a) [Linux only] have been given CAP_NET_BIND_SERVICE capabilities using e.g. setcap or systemd's AmbientCapabilities, or (b) start as root.", port);
} else {
die("nqptp is unable to listen on port %u. The error is: %d, \"%s\".", port, errno, strerror(errno));
}
Expand Down
44 changes: 38 additions & 6 deletions nqptp.c
Original file line number Diff line number Diff line change
Expand Up @@ -48,11 +48,17 @@
#include <netdb.h>
#include <sys/socket.h>

#ifdef CONFIG_FOR_FREEBSD
#if defined(CONFIG_FOR_FREEBSD) || defined(CONFIG_FOR_OPENBSD)
#include <netinet/in.h>
#include <sys/socket.h>
#endif

#ifdef CONFIG_FOR_OPENBSD
#include <sys/types.h>
#include <unistd.h>
#include <pwd.h>
#endif

#ifndef FIELD_SIZEOF
#define FIELD_SIZEOF(t, f) (sizeof(((t *)0)->f))
#endif
Expand Down Expand Up @@ -125,6 +131,11 @@ void termHandler(__attribute__((unused)) int k) {
}

int main(int argc, char **argv) {
#ifdef CONFIG_FOR_OPENBSD
if (pledge("stdio rpath tmppath inet dns id", NULL) == -1) {
die("pledge: %s", strerror(errno));
}
#endif

int debug_level = 0;
int i;
Expand Down Expand Up @@ -177,6 +188,10 @@ int main(int argc, char **argv) {

sockets_open_stuff.sockets_open = 0;

// open PTP sockets
open_sockets_at_port(NULL, 319, &sockets_open_stuff);
open_sockets_at_port(NULL, 320, &sockets_open_stuff);

epoll_fd = -1;

// control-c (SIGINT) cleanly
Expand All @@ -191,6 +206,26 @@ int main(int argc, char **argv) {
act2.sa_handler = termHandler;
sigaction(SIGTERM, &act2, NULL);

#ifdef CONFIG_FOR_OPENBSD
// shm_open(3) prohibits sharing between different UIDs, so nqptp must run as
// the same user shairport-sync does.
struct passwd *pw;
const char *shairport_user = "_shairport";
pw = getpwnam(shairport_user);
if (pw == NULL) {
die("unknown user %s", shairport_user);
}
if (setgroups(1, &pw->pw_gid) == -1 ||
setresgid(pw->pw_gid, pw->pw_gid, pw->pw_gid) == -1 ||
setresuid(pw->pw_uid, pw->pw_uid, pw->pw_uid) == -1) {
die("cannot drop privileges to %s", shairport_user);
}

if (pledge("stdio tmppath inet dns", NULL) == -1) {
die("pledge: %s", strerror(errno));
}
#endif

// open the SMI

shm_fd = -1;
Expand All @@ -206,7 +241,7 @@ int main(int argc, char **argv) {
die("failed to set size of shared memory \"%s\".", NQPTP_INTERFACE_NAME);
}

#ifdef CONFIG_FOR_FREEBSD
#if defined(CONFIG_FOR_FREEBSD) || defined(CONFIG_FOR_OPENBSD)
shared_memory = (struct shm_structure *)mmap(NULL, sizeof(struct shm_structure),
PROT_READ | PROT_WRITE, MAP_SHARED, shm_fd, 0);
#endif
Expand All @@ -233,10 +268,7 @@ int main(int argc, char **argv) {

char buf[BUFLEN];

// open sockets 319 and 320

open_sockets_at_port(NULL, 319, &sockets_open_stuff);
open_sockets_at_port(NULL, 320, &sockets_open_stuff);
// open control socket
open_sockets_at_port("localhost", NQPTP_CONTROL_PORT,
&sockets_open_stuff); // this for messages from the client

Expand Down