Hello community, here is the log from the commit of package llmnrd for openSUSE:Factory checked in at 2020-09-21 17:39:33 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Comparing /work/SRC/openSUSE:Factory/llmnrd (Old) and /work/SRC/openSUSE:Factory/.llmnrd.new.4249 (New) ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Package is "llmnrd" Mon Sep 21 17:39:33 2020 rev:6 rq:835457 version:0.7 Changes: -------- --- /work/SRC/openSUSE:Factory/llmnrd/llmnrd.changes 2019-02-01 11:45:33.804545214 +0100 +++ /work/SRC/openSUSE:Factory/.llmnrd.new.4249/llmnrd.changes 2020-09-21 17:43:15.148903373 +0200 @@ -1,0 +2,11 @@ +Mon Sep 14 18:51:31 UTC 2020 - Martin Hauke <[email protected]> + +- Update to version 0.7 + * set stdout to line buffering + * don't exit on SO_BINDTODEVICE failure + * create pid file when daemonizing, and remove it on exit + * add command line option to log to syslog instead of stdio + * only async signal safe functions may be called in signal handler + * exit gracefully on select() EINTR + +------------------------------------------------------------------- Old: ---- llmnrd-0.6.tar.gz New: ---- llmnrd-0.7.tar.gz ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Other differences: ------------------ ++++++ llmnrd.spec ++++++ --- /var/tmp/diff_new_pack.sEOTei/_old 2020-09-21 17:43:16.824904952 +0200 +++ /var/tmp/diff_new_pack.sEOTei/_new 2020-09-21 17:43:16.828904956 +0200 @@ -1,8 +1,8 @@ # # spec file for package llmnrd # -# Copyright (c) 2019 SUSE LINUX GmbH, Nuernberg, Germany. -# Copyright (c) 2017, Martin Hauke <[email protected]> +# Copyright (c) 2020 SUSE LLC +# Copyright (c) 2017-2020, Martin Hauke <[email protected]> # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed @@ -13,7 +13,7 @@ # license that conforms to the Open Source Definition (Version 1.9) # published by the Open Source Initiative. -# Please submit bugfixes or comments via http://bugs.opensuse.org/ +# Please submit bugfixes or comments via https://bugs.opensuse.org/ # @@ -22,7 +22,7 @@ %define _fillupdir %{_localstatedir}/adm/fillup-templates %endif Name: llmnrd -Version: 0.6 +Version: 0.7 Release: 0 Summary: Link-Local Multicast Resolution (LLMNR) Daemon License: GPL-2.0-only ++++++ llmnrd-0.6.tar.gz -> llmnrd-0.7.tar.gz ++++++ diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/llmnrd-0.6/Makefile new/llmnrd-0.7/Makefile --- old/llmnrd-0.6/Makefile 2019-01-29 10:04:04.000000000 +0100 +++ new/llmnrd-0.7/Makefile 2020-09-14 12:21:49.000000000 +0200 @@ -2,17 +2,17 @@ # # Copyright (C) 2014-2019 Tobias Klauser <[email protected]> -VERSION = 0.6 +VERSION = 0.7 # llmnrd binary D_P = llmnrd -D_OBJS = llmnr.o iface.o socket.o util.o llmnrd.o +D_OBJS = llmnr.o iface.o socket.o util.o log.o llmnrd.o D_LIBS = D_MAN = $(D_P).8 # llmnr-query binary Q_P = llmnr-query -Q_OBJS = util.o llmnr-query.o +Q_OBJS = util.o log.o llmnr-query.o Q_LIBS = Q_MAN = $(Q_P).1 @@ -29,7 +29,13 @@ GIT_VERSION = endif -CFLAGS_MIN := -W -Wall -DVERSION_STRING=\"v$(VERSION)\" -DGIT_VERSION=\"$(GIT_VERSION)\" +PIDFILE ?= /run/llmnrd/pid + +CFLAGS_MIN := -W -Wall \ + -DVERSION_STRING=\"v$(VERSION)\" \ + -DGIT_VERSION=\"$(GIT_VERSION)\" \ + -DPIDFILE=\"$(PIDFILE)\" + ifeq ($(DEBUG), 1) CFLAGS_MIN += -g -DDEBUG endif diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/llmnrd-0.6/README.md new/llmnrd-0.7/README.md --- old/llmnrd-0.6/README.md 2019-01-29 10:04:04.000000000 +0100 +++ new/llmnrd-0.7/README.md 2020-09-14 12:21:49.000000000 +0200 @@ -97,6 +97,7 @@ The following people contributed patches and ideas, found and reported bugs or otherwise helped in the development of llmnrd: +* Diego Santa Cruz (@diego-santacruz) * Elazar Leibovich (@elazarl) * Martin Hauke * Michael Evertz (@dvl-mevertz) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/llmnrd-0.6/etc/llmnrd-init-script new/llmnrd-0.7/etc/llmnrd-init-script --- old/llmnrd-0.6/etc/llmnrd-init-script 1970-01-01 01:00:00.000000000 +0100 +++ new/llmnrd-0.7/etc/llmnrd-init-script 2020-09-14 12:21:49.000000000 +0200 @@ -0,0 +1,172 @@ +#!/bin/sh +# +# License: Copyright 2020 SpinetiX. This file is licensed +# under the terms of the GNU General Public License version 2. +# This program is licensed "as is" without any warranty of any +# kind, whether express or implied. +# +# Copyright 1999-2003 MontaVista Software, Inc. +# Copyright 2002, 2003, 2004 Sony Corporation +# Copyright 2002, 2003, 2004 Matsushita Electric Industrial Co., Ltd. +# +### BEGIN INIT INFO +# Required-Start: +# Required-Stop: +# Should-Start: +# Should-Stop: +# Default-Start: 2 3 5 +# Default-Stop: +# Short-Description: Starting/stopping llmnrd +# Description: Starting/stopping llmnrd +### END INIT INFO + +# Init script information +NAME=llmnrd +DESC="llmnrd" + +# Individual Daemon information +DAEMON=/usr/sbin/llmnrd +ARGS="-6 -d -s" +BASENAME=llmnrd + +# Load init script configuration +DISABLE_LLMNRD= +[ -f /etc/default/$NAME ] && . /etc/default/$NAME + +# Source the init script functions +. /etc/init.d/functions + +# Verify daemons are installed +if [ ! -x $DAEMON -a "$1" != "stop" ]; then + echo -n "Not starting $DESC $NAME, $DAEMON not installed" + echo + exit 0 +fi + +if [ -n "$DISABLE_LLMNRD" -a "$1" != "stop" ]; then + echo -n "Not starting $DESC $NAME, disabled via /etc/default/$NAME" + echo + exit 0 +fi + +start() { + local RET + + echo -n "Starting $DESC: " + + echo -n "$NAME " + + start-stop-daemon --start -u llmnrd -n llmnrd -p /run/llmnrd/pid -c llmnrd -x $DAEMON -- $ARGS + RET=$? + if [ $RET -eq 0 ]; then + success; echo + else + failure; echo + return 1 + fi + + return 0 +} + +stop () { + local RET + + echo -n "Stopping $DESC: $NAME " + start-stop-daemon --stop -u llmnrd -n llmnrd -p /run/llmnrd/pid -q + RET=$? + if [ $RET -eq 0 ]; then + success; echo + else + failure; echo + return 1 + fi + + return 0 +} + +restart() { + local RET + + echo "Restarting $DESC..." + stop + start + RET=$? + + return $RET +} + +condrestart() { + local RET + + pidofproc $BASENAME >/dev/null + RET=$? + if [ $RET -eq 0 ]; then + restart + RET=$? + else + RET=1 + fi + + return $RET +} + +reload() { + local RET pid + + # llmnrd has no support for HUP, so just restart + condrestart +} + +forcereload() { + local RET + + reload + RET=$? + if [ $RET -ne 0 ]; then + restart + RET=$? + fi + + return $RET +} + +parse() { + case "$1" in + start) + start + return $? + ;; + stop) + stop + return $? + ;; + restart) + restart + return $? + ;; + condrestart|try-restart) + condrestart + return $? + ;; + reload) + reload + return $? + ;; + force-reload) + forcereload + return $? + ;; + status) + status $BASENAME + return $? + ;; + *) + echo "Usage: $NAME " \ + "{start|stop|restart|condrestart|reload|force-reload|status}" >&2 + ;; + esac + + return 1 +} + +parse $@ diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/llmnrd-0.6/iface.c new/llmnrd-0.7/iface.c --- old/llmnrd-0.6/iface.c 2019-01-29 10:04:04.000000000 +0100 +++ new/llmnrd-0.7/iface.c 2020-09-14 12:21:49.000000000 +0200 @@ -319,18 +319,24 @@ log_err("Failed to enumerate rtnl interfaces: %s\n", strerror(errno)); } -void iface_init(int sock, const char *iface, bool ipv6, +int iface_init(int sock, const char *iface, bool ipv6, iface_event_handler_t event_handler) { INIT_LIST_HEAD(&iface_list_head); iface_event_handler = event_handler; - if (iface) + if (iface) { iface_ifindex = if_nametoindex(iface); + if (!iface_ifindex) { + log_err("Interface %s not found: %s\n", iface, strerror(errno)); + return -1; + } + } /* send RTM_GETADDR request to initially populate the interface list */ iface_rtnl_enumerate(sock, RTM_GETADDR, AF_INET); if (ipv6) iface_rtnl_enumerate(sock, RTM_GETADDR, AF_INET6); + return 0; } int iface_recv(int sock) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/llmnrd-0.6/iface.h new/llmnrd-0.7/iface.h --- old/llmnrd-0.6/iface.h 2019-01-29 10:04:04.000000000 +0100 +++ new/llmnrd-0.7/iface.h 2020-09-14 12:21:49.000000000 +0200 @@ -30,7 +30,7 @@ typedef void (*iface_event_handler_t)(enum iface_event_type, unsigned char af, unsigned int ifindex); -void iface_init(int sock, const char *iface, bool ipv6, +int iface_init(int sock, const char *iface, bool ipv6, iface_event_handler_t event_handler); int iface_recv(int sock); diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/llmnrd-0.6/llmnr.c new/llmnrd-0.7/llmnr.c --- old/llmnrd-0.6/llmnr.c 2019-01-29 10:04:04.000000000 +0100 +++ new/llmnrd-0.7/llmnr.c 2020-09-14 12:21:49.000000000 +0200 @@ -188,7 +188,7 @@ pkt_free(p); } -static void llmnr_packet_process(unsigned int ifindex, const uint8_t *pktbuf, size_t len, +static void llmnr_packet_process(int ifindex, const uint8_t *pktbuf, size_t len, int sock, const struct sockaddr_storage *sst) { const struct llmnr_hdr *hdr = (const struct llmnr_hdr *)pktbuf; diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/llmnrd-0.6/llmnrd.c new/llmnrd-0.7/llmnrd.c --- old/llmnrd-0.6/llmnrd.c 2019-01-29 10:04:04.000000000 +0100 +++ new/llmnrd-0.7/llmnrd.c 2020-09-14 12:21:49.000000000 +0200 @@ -49,13 +49,14 @@ static int llmnrd_sock_ipv6 = -1; static int llmnrd_fd_hostname = -1; -static const char *short_opts = "H:i:p:6dhV"; +static const char *short_opts = "H:i:p:6dshV"; static const struct option long_opts[] = { { "hostname", required_argument, NULL, 'H' }, { "interface", required_argument, NULL, 'i' }, { "port", required_argument, NULL, 'p' }, { "ipv6", no_argument, NULL, '6' }, { "daemonize", no_argument, NULL, 'd' }, + { "syslog", no_argument, NULL, 's' }, { "help", no_argument, NULL, 'h' }, { "version", no_argument, NULL, 'V' }, { NULL, 0, NULL, 0 }, @@ -70,6 +71,7 @@ " -p, --port NUM set port number to listen on (default: %d)\n" " -6, --ipv6 enable LLMNR name resolution over IPv6\n" " -d, --daemonize run as daemon in the background\n" + " -s, --syslog send all log output to syslog\n" " -h, --help show this help and exit\n" " -V, --version show version information and exit\n", LLMNR_UDP_PORT); @@ -91,7 +93,6 @@ case SIGINT: case SIGQUIT: case SIGTERM: - log_info("Interrupt received. Stopping llmnrd.\n"); llmnrd_running = false; break; case SIGHUP: @@ -150,6 +151,37 @@ free(newname); } +static bool write_pid_file(void) +{ + int fd; + char buf[64]; + ssize_t len; + + fd = open(PIDFILE, O_CREAT|O_EXCL|O_RDWR, 0644); + if (fd == -1) { + log_err("Failed to open pid file %s: %s", PIDFILE, strerror(errno)); + return false; + } + + if (snprintf(buf, sizeof(buf), "%ji\n", (intmax_t) getpid()) < 0) + goto err; + + len = strlen(buf); + if (write(fd, buf, len) != len) + goto err; + + close(fd); + return true; + +err: + log_err("Failed to write pid to %s", PIDFILE); + if (fd != -1) { + unlink(PIDFILE); + close(fd); + } + return false; +} + int main(int argc, char **argv) { int c, ret = -1; @@ -159,13 +191,20 @@ char *iface = NULL; uint16_t port = LLMNR_UDP_PORT; int llmnrd_sock_rtnl = -1; + bool rm_pid_file = false; int nfds; + setlinebuf(stdout); + while ((c = getopt_long(argc, argv, short_opts, long_opts, NULL)) != -1) { switch (c) { case 'd': daemonize = true; break; + case 's': + openlog("llmnrd", LOG_PID, LOG_DAEMON); + log_to_syslog(); + break; case 'H': hostname = xstrdup(optarg); break; @@ -213,6 +252,9 @@ log_err("Failed to daemonize process: %s\n", strerror(errno)); goto out; } + if (!write_pid_file()) + goto out; + rm_pid_file = true; } log_info("Starting llmnrd on port %u, hostname %s\n", port, hostname); @@ -234,7 +276,10 @@ goto out; llmnr_init(hostname, ipv6); - iface_init(llmnrd_sock_rtnl, iface, ipv6, &iface_event_handle); + + ret = iface_init(llmnrd_sock_rtnl, iface, ipv6, &iface_event_handle); + if (ret < 0) + goto out; nfds = max(llmnrd_sock_ipv4, llmnrd_sock_rtnl); if (llmnrd_sock_ipv6 >= 0) @@ -258,9 +303,10 @@ ret = select(nfds, &rfds, NULL, &efds, NULL); if (ret < 0) { - if (errno != EINTR) + if (errno != EINTR) { log_err("Failed to select() on socket: %s\n", strerror(errno)); - goto out; + goto out; + } } else if (ret) { /* handle RTNL messages first so we can respond with * up-to-date information. @@ -276,6 +322,8 @@ } } + log_info("Signal received. Stopping llmnrd.\n"); + ret = 0; out: if (llmnrd_sock_rtnl >= 0) @@ -285,5 +333,7 @@ if (llmnrd_sock_ipv4 >= 0) close(llmnrd_sock_ipv4); free(hostname); + if (rm_pid_file) + unlink(PIDFILE); return ret == 0 ? EXIT_SUCCESS : EXIT_FAILURE; } diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/llmnrd-0.6/log.c new/llmnrd-0.7/log.c --- old/llmnrd-0.6/log.c 1970-01-01 01:00:00.000000000 +0100 +++ new/llmnrd-0.7/log.c 2020-09-14 12:21:49.000000000 +0200 @@ -0,0 +1,39 @@ +#include <stdarg.h> +#include <stdbool.h> + +#include "log.h" + +static bool use_syslog; + +void log_lvl(int lvl, const char *fmt, ...) +{ + va_list ap; + + va_start(ap, fmt); + + if (!use_syslog) { + FILE *out = stderr; + switch (lvl) { + case LOG_ERR: + fputs("Error: ", stderr); + break; + case LOG_WARNING: + fputs("Warning: ", stderr); + break; + case LOG_INFO: + case LOG_DEBUG: + out = stdout; + break; + } + vfprintf(out, fmt, ap); + } else { + vsyslog(lvl, fmt, ap); + } + + va_end(ap); +} + +void log_to_syslog(void) +{ + use_syslog = true; +} diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/llmnrd-0.6/log.h new/llmnrd-0.7/log.h --- old/llmnrd-0.6/log.h 2019-01-29 10:04:04.000000000 +0100 +++ new/llmnrd-0.7/log.h 2020-09-14 12:21:49.000000000 +0200 @@ -20,12 +20,19 @@ #define LOG_H #include <stdio.h> +#include <syslog.h> -#define log_err(fmt, args...) fprintf(stderr, "Error: " fmt, ##args) -#define log_warn(fmt, args...) fprintf(stderr, "Warning: " fmt, ##args) -#define log_info(fmt, args...) fprintf(stdout, fmt, ##args) +#include "compiler.h" + +void log_lvl(int lvl, const char *fmt, ...) __check_format_printf(2, 3); + +void log_to_syslog(void); + +#define log_err(fmt, args...) log_lvl(LOG_ERR, fmt, ##args) +#define log_warn(fmt, args...) log_lvl(LOG_WARNING, fmt, ##args) +#define log_info(fmt, args...) log_lvl(LOG_INFO, fmt, ##args) #ifdef DEBUG -# define log_dbg(fmt, args...) fprintf(stdout, fmt, ##args) +# define log_dbg(fmt, args...) log_lvl(LOG_DEBUG, fmt, ##args) #else # define log_dbg(fmt, args...) #endif diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/llmnrd-0.6/socket.c new/llmnrd-0.7/socket.c --- old/llmnrd-0.6/socket.c 2019-01-29 10:04:04.000000000 +0100 +++ new/llmnrd-0.7/socket.c 2020-09-14 12:21:49.000000000 +0200 @@ -36,7 +36,7 @@ static const int YES = 1; static const int TTL = 255; -static int socket_bind_to_device(int sock, const char *iface) { +static void socket_bind_to_device(int sock, const char *iface) { #ifdef SO_BINDTODEVICE /* bind socket to specific interface */ if (iface) { @@ -45,12 +45,10 @@ memset(&ifr, 0, sizeof(ifr)); strncpy(ifr.ifr_name, iface, sizeof(ifr.ifr_name) - 1); if (setsockopt(sock, SOL_SOCKET, SO_BINDTODEVICE, &ifr, sizeof(ifr)) < 0) { - log_err("Failed to bind socket to device %s: %s\n", iface, strerror(errno)); - return -1; + log_warn("Failed to bind socket to device %s: %s\n", iface, strerror(errno)); } } #endif - return 0; } int socket_open_ipv4(uint16_t port, const char *iface) @@ -81,8 +79,7 @@ goto err; } - if (socket_bind_to_device(sock, iface) < 0) - goto err; + socket_bind_to_device(sock, iface); /* bind the socket */ memset(&sa, 0, sizeof(sa)); @@ -140,8 +137,7 @@ goto err; } - if (socket_bind_to_device(sock, iface) < 0) - goto err; + socket_bind_to_device(sock, iface); /* bind the socket */ memset(&sa, 0, sizeof(sa));
