=== modified file 'Makefile' --- Makefile 2018-02-22 18:50:12 +0000 +++ Makefile 2018-08-19 14:32:00 +0000 @@ -89,8 +89,7 @@ # Do not change these two CFLAGS+=$(WARN) $(DEBUG) $(FORTIFY) $(SANITIZE) $(COVERAGE) \ - $(OPTIMIZE) $(LANGUAGE) $(GNUTLS_CFLAGS) $(AVAHI_CFLAGS) \ - $(GPGME_CFLAGS) -DVERSION='"$(version)"' + $(OPTIMIZE) $(LANGUAGE) -DVERSION='"$(version)"' LDFLAGS+=-Xlinker --as-needed $(COVERAGE) $(LINK_FORTIFY) $(foreach flag,$(LINK_FORTIFY_LD),-Xlinker $(flag)) # Commands to format a DocBook document into a manual page @@ -257,6 +256,7 @@ # -fsanitize=leak because GnuTLS and GPGME both leak memory. plugins.d/mandos-client: plugins.d/mandos-client.c $(CC) $(filter-out -fsanitize=leak,$(CFLAGS)) $(strip\ + ) $(GNUTLS_CFLAGS) $(AVAHI_CFLAGS) $(GPGME_CFLAGS) $(strip\ ) $(CPPFLAGS) $(LDFLAGS) $(TARGET_ARCH) $^ $(strip\ ) -lrt $(GNUTLS_LIBS) $(AVAHI_LIBS) $(strip\ ) $(GPGME_LIBS) $(LOADLIBES) $(LDLIBS) -o $@ @@ -396,6 +396,8 @@ "$(CONFDIR)/network-hooks.d" install --mode=u=rwx,go=rx \ --target-directory=$(LIBDIR)/mandos plugin-runner + install --mode=u=rwx,go=rx \ + --target-directory=$(LIBDIR)/mandos mandos-to-cryptroot-unlock install --mode=u=rwx,go=rx --target-directory=$(PREFIX)/sbin \ mandos-keygen install --mode=u=rwx,go=rx \ @@ -421,10 +423,12 @@ plugin-helpers/mandos-client-iprouteadddel install initramfs-tools-hook \ $(INITRAMFSTOOLS)/hooks/mandos - install --mode=u=rw,go=r initramfs-tools-hook-conf \ - $(INITRAMFSTOOLS)/conf-hooks.d/mandos + install --mode=u=rw,go=r initramfs-tools-conf \ + $(INITRAMFSTOOLS)/conf.d/mandos-conf install initramfs-tools-script \ $(INITRAMFSTOOLS)/scripts/init-premount/mandos + install initramfs-tools-script-stop \ + $(INITRAMFSTOOLS)/scripts/local-premount/mandos install --mode=u=rw,go=r plugin-runner.conf $(CONFDIR) gzip --best --to-stdout mandos-keygen.8 \ > $(MANDIR)/man8/mandos-keygen.8.gz === modified file 'debian/control' --- debian/control 2018-02-10 18:47:22 +0000 +++ debian/control 2018-08-19 16:15:46 +0000 @@ -11,10 +11,11 @@ xsltproc, pkg-config, libnl-route-3-dev Build-Depends-Indep: systemd, python (>= 2.7), python (<< 3), python-dbus, python-gi -Standards-Version: 4.1.3 +Standards-Version: 4.2.0 Vcs-Bzr: https://ftp.recompile.se/pub/mandos/trunk Vcs-Browser: https://bzr.recompile.se/loggerhead/mandos/trunk/files Homepage: https://www.recompile.se/mandos +Rules-Requires-Root: binary-targets Package: mandos Architecture: all @@ -42,7 +43,7 @@ Package: mandos-client Architecture: linux-any Depends: ${shlibs:Depends}, ${misc:Depends}, adduser, cryptsetup, - initramfs-tools, dpkg-dev (>=1.16.0) + initramfs-tools (>= 0.99), dpkg-dev (>=1.16.0) Recommends: ssh, gnutls-bin | openssl Breaks: dropbear (<= 0.53.1-1) Enhances: cryptsetup === modified file 'debian/mandos-client.dirs' --- debian/mandos-client.dirs 2009-02-07 04:50:39 +0000 +++ debian/mandos-client.dirs 2018-08-19 14:32:00 +0000 @@ -1,5 +1,6 @@ usr/share/man/man8 usr/sbin usr/share/initramfs-tools/hooks -usr/share/initramfs-tools/conf-hooks.d +usr/share/initramfs-tools/conf.d usr/share/initramfs-tools/scripts/init-premount +usr/share/initramfs-tools/scripts/local-premount === added file 'initramfs-tools-conf' --- initramfs-tools-conf 1970-01-01 00:00:00 +0000 +++ initramfs-tools-conf 2018-08-19 14:06:55 +0000 @@ -0,0 +1,17 @@ +# -*- shell-script -*- + +# Since the initramfs image will contain key files, we need to +# restrict permissions on it by setting UMASK here. +# +# The proper place to set UMASK is (according to +# /etc/cryptsetup-initramfs/conf-hook), in +# /etc/initramfs-tools/initramfs.conf, which we shouldn't edit. The +# corresponding directory for drop-in files from packages is +# /usr/share/initramfs-tools/conf.d, and this file will be installed +# there as "mandos-conf". +# +# This setting of UMASK will have unfortunate unintended side effects +# on the files *inside* the initramfs, but these are later fixed by +# "initramfs-tools-hook", installed as +# "/usr/share/initramfs-tools/hooks/mandos". +UMASK=0027 === modified file 'initramfs-tools-hook' --- initramfs-tools-hook 2017-02-21 22:15:43 +0000 +++ initramfs-tools-hook 2018-08-19 14:06:55 +0000 @@ -80,6 +80,8 @@ --mode=u=rwx "${DESTDIR}${PLUGINDIR}" \ "${DESTDIR}${PLUGINHELPERDIR}" +copy_exec "$libdir"/mandos/mandos-to-cryptroot-unlock "${MANDOSDIR}" + # Copy the Mandos plugin runner copy_exec "$libdir"/mandos/plugin-runner "${MANDOSDIR}" @@ -250,8 +252,8 @@ # initrd; it is intended to affect the initrd.img file itself, since # it now contains secret key files. There is, however, no other way # to set the permission of the initrd.img file without a race -# condition. This umask is set by "initramfs-tools-hook-conf", -# installed as "/usr/share/initramfs-tools/conf-hooks.d/mandos".) +# condition. This umask is set by "initramfs-tools-conf", installed +# as "/usr/share/initramfs-tools/conf.d/mandos-conf".) # for full in "${MANDOSDIR}" "${CONFDIR}"; do while [ "$full" != "/" ]; do === removed file 'initramfs-tools-hook-conf' --- initramfs-tools-hook-conf 2009-05-17 00:50:09 +0000 +++ initramfs-tools-hook-conf 1970-01-01 00:00:00 +0000 @@ -1,13 +0,0 @@ -# -*- shell-script -*- - -# if mkinitramfs is started by mkinitramfs-kpkg, mkinitramfs-kpkg has -# already touched the initrd file with umask 022 before we had a -# chance to affect it. We cannot allow a readable initrd file, -# therefore we must fix this now. -if [ -e "${outfile}" ] \ - && [ `stat --format=%s "${outfile}"` -eq 0 ]; then - rm "${outfile}" - (umask 027; touch "${outfile}") -fi - -UMASK=027 === modified file 'initramfs-tools-script' --- initramfs-tools-script 2017-08-20 14:41:20 +0000 +++ initramfs-tools-script 2018-08-19 01:35:11 +0000 @@ -51,9 +51,6 @@ chmod a=rwxt /tmp -test -r /conf/conf.d/cryptroot -test -w /conf/conf.d - # Get DEVICE from /conf/initramfs.conf and other files . /conf/initramfs.conf for conf in /conf/conf.d/*; do @@ -105,74 +102,80 @@ fi fi -# Do not replace cryptroot file unless we need to. -replace_cryptroot=no - -# Our keyscript -mandos=/lib/mandos/plugin-runner -test -x "$mandos" - -# parse /conf/conf.d/cryptroot. Format: -# target=sda2_crypt,source=/dev/sda2,rootdev,key=none,keyscript=/foo/bar/baz -# Is the root device specially marked? -changeall=yes -while read -r options; do - case "$options" in - rootdev,*|*,rootdev,*|*,rootdev) - # If the root device is specially marked, don't change all - # lines in crypttab by default. - changeall=no - ;; - esac -done < /conf/conf.d/cryptroot - -exec 3>/conf/conf.d/cryptroot.mandos -while read -r options; do - newopts="" - keyscript="" - changethis="$changeall" - # Split option line on commas - old_ifs="$IFS" - IFS="$IFS," - for opt in $options; do - # Find the keyscript option, if any - case "$opt" in - keyscript=*) - keyscript="${opt#keyscript=}" - newopts="$newopts,$opt" - ;; - "") : ;; - # Always use Mandos on the root device, if marked - rootdev) - changethis=yes - newopts="$newopts,$opt" - ;; - # Don't use Mandos on resume device, if marked - resumedev) - changethis=no - newopts="$newopts,$opt" - ;; - *) - newopts="$newopts,$opt" +if [ -r /conf/conf.d/cryptroot ]; then + test -w /conf/conf.d + + # Do not replace cryptroot file unless we need to. + replace_cryptroot=no + + # Our keyscript + mandos=/lib/mandos/plugin-runner + test -x "$mandos" + + # parse /conf/conf.d/cryptroot. Format: + # target=sda2_crypt,source=/dev/sda2,rootdev,key=none,keyscript=/foo/bar/baz + # Is the root device specially marked? + changeall=yes + while read -r options; do + case "$options" in + rootdev,*|*,rootdev,*|*,rootdev) + # If the root device is specially marked, don't change all + # lines in crypttab by default. + changeall=no ;; esac - done - IFS="$old_ifs" - unset old_ifs - # If there was no keyscript option, add one. - if [ "$changethis" = yes ] && [ -z "$keyscript" ]; then - replace_cryptroot=yes - newopts="$newopts,keyscript=$mandos" + done < /conf/conf.d/cryptroot + + exec 3>/conf/conf.d/cryptroot.mandos + while read -r options; do + newopts="" + keyscript="" + changethis="$changeall" + # Split option line on commas + old_ifs="$IFS" + IFS="$IFS," + for opt in $options; do + # Find the keyscript option, if any + case "$opt" in + keyscript=*) + keyscript="${opt#keyscript=}" + newopts="$newopts,$opt" + ;; + "") : ;; + # Always use Mandos on the root device, if marked + rootdev) + changethis=yes + newopts="$newopts,$opt" + ;; + # Don't use Mandos on resume device, if marked + resumedev) + changethis=no + newopts="$newopts,$opt" + ;; + *) + newopts="$newopts,$opt" + ;; + esac + done + IFS="$old_ifs" + unset old_ifs + # If there was no keyscript option, add one. + if [ "$changethis" = yes ] && [ -z "$keyscript" ]; then + replace_cryptroot=yes + newopts="$newopts,keyscript=$mandos" + fi + newopts="${newopts#,}" + echo "$newopts" >&3 + done < /conf/conf.d/cryptroot + exec 3>&- + + # If we need to, replace the old cryptroot file with the new file. + if [ "$replace_cryptroot" = yes ]; then + mv /conf/conf.d/cryptroot /conf/conf.d/cryptroot.mandos-old + mv /conf/conf.d/cryptroot.mandos /conf/conf.d/cryptroot + else + rm -f /conf/conf.d/cryptroot.mandos fi - newopts="${newopts#,}" - echo "$newopts" >&3 -done < /conf/conf.d/cryptroot -exec 3>&- - -# If we need to, replace the old cryptroot file with the new file. -if [ "$replace_cryptroot" = yes ]; then - mv /conf/conf.d/cryptroot /conf/conf.d/cryptroot.mandos-old - mv /conf/conf.d/cryptroot.mandos /conf/conf.d/cryptroot -else - rm /conf/conf.d/cryptroot.mandos +elif [ -x /usr/bin/cryptroot-unlock ]; then + setsid /lib/mandos/mandos-to-cryptroot-unlock & fi === added file 'initramfs-tools-script-stop' --- initramfs-tools-script-stop 1970-01-01 00:00:00 +0000 +++ initramfs-tools-script-stop 2018-08-19 14:58:40 +0000 @@ -0,0 +1,65 @@ +#!/bin/sh -e +# +# Script to wait for plugin-runner to exit before continuing boot +# +# Copyright © 2018 Teddy Hogeborn +# Copyright © 2018 Björn Påhlsson +# +# This file is part of Mandos. +# +# Mandos is free software: you can redistribute it and/or modify it +# under the terms of the GNU General Public License as published by +# the Free Software Foundation, either version 3 of the License, or +# (at your option) any later version. +# +# Mandos is distributed in the hope that it will be useful, but +# WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with Mandos. If not, see . +# +# Contact the authors at . +# +# This script will run in the initrd environment at boot and remove +# the file keeping the dummy plugin running, forcing plugin-runner to +# exit if it is still running. + +# This script should be installed as +# "/usr/share/initramfs-tools/scripts/local-premount/mandos" which will +# eventually be "/scripts/local-premount/mandos" in the initrd.img +# file. + +PREREQ="" +prereqs() +{ + echo "$PREREQ" +} + +case $1 in +prereqs) + prereqs + exit 0 + ;; +esac + +. /scripts/functions + +pid=$(cat /run/mandos-plugin-runner.pid 2>/dev/null) + +# If the dummy plugin is running, removing this file should force the +# dummy plugin to exit successfully, thereby making plugin-runner shut +# down all its other plugins and then exit itself. +rm -f /run/mandos-keep-running >/dev/null 2>&1 + +# Wait for exit of plugin-runner, if still running +if [ -n "$pid" ]; then + while :; do + case "$(readlink /proc/"$pid"/exe 2>/dev/null)" in + */plugin-runner) sleep 1;; + *) break;; + esac + done + rm -f /run/mandos-plugin-runner.pid >/dev/null 2>&1 +fi === modified file 'mandos' --- mandos 2018-02-22 18:50:12 +0000 +++ mandos 2018-08-15 09:18:22 +0000 @@ -2365,7 +2365,8 @@ ctypes.byref(crtverify)) if crtverify.value != 0: gnutls.openpgp_crt_deinit(crt) - raise gnutls.CertificateSecurityError("Verify failed") + raise gnutls.CertificateSecurityError(code + =crtverify.value) # New buffer for the fingerprint buf = ctypes.create_string_buffer(20) buf_len = ctypes.c_size_t() === added file 'mandos-to-cryptroot-unlock' --- mandos-to-cryptroot-unlock 1970-01-01 00:00:00 +0000 +++ mandos-to-cryptroot-unlock 2018-08-19 14:58:40 +0000 @@ -0,0 +1,82 @@ +#!/bin/sh +# +# Script to get password from plugin-runner to cryptroot-unlock +# +# Copyright © 2018 Teddy Hogeborn +# Copyright © 2018 Björn Påhlsson +# +# This file is part of Mandos. +# +# Mandos is free software: you can redistribute it and/or modify it +# under the terms of the GNU General Public License as published by +# the Free Software Foundation, either version 3 of the License, or +# (at your option) any later version. +# +# Mandos is distributed in the hope that it will be useful, but +# WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with Mandos. If not, see . +# +# Contact the authors at . + +# This script is made to run in the initramfs, and must not be run in +# the normal system environment. + +# Temporary file for the password +passfile=$(mktemp -p /run -t mandos.XXXXXX) +trap "rm -f -- $passfile 2>/dev/null" EXIT + +# Disable the plugins which conflict with "askpass" as distributed by +# cryptsetup. +cat <<-EOF >>/conf/conf.d/mandos/plugin-runner.conf + + --disable=askpass-fifo + --disable=password-prompt + --disable=plymouth +EOF + +# In case a password is retrieved by other means than by plugin-runner +# (such as typing it on the console into the prompt given by the +# "askpass" program), this dummy plugin will be made to exit +# successfully, thereby forcing plugin-runner to stop all its plugins +# and also exit itself. +cat <<-EOF > /lib/mandos/plugins.d/dummy + #!/bin/sh + + while [ -e /run/mandos-keep-running ]; do + sleep 1 + done + + # exit successfully to force plugin-runner to finish + exit 0 +EOF +chmod u=rwx,go=rx /lib/mandos/plugins.d/dummy + +# This file is the flag which keeps the dummy plugin running +touch /run/mandos-keep-running + +# Keep running plugin-runner and trying any password, until either a +# password is accepted by cryptroot-unlock, or plugin-runner fails, or +# the file /run/mandos-keep-running has been removed. +while type cryptroot-unlock >/dev/null 2>&1; do + /lib/mandos/plugin-runner > "$passfile" & + echo $! > /run/mandos-plugin-runner.pid + wait %% || break + + # Try this password ten times (or ten seconds) + for loop in 1 2 3 4 5 6 7 8 9 10; do + if [ -e /run/mandos-keep-running ]; then + cryptroot-unlock < "$passfile" >/dev/null 2>&1 && break 2 + sleep 1 + else + break 2 + fi + done +done + +exec >/dev/null 2>&1 + +rm -f /run/mandos-plugin-runner.pid /run/mandos-keep-running === modified file 'plugin-runner.c' --- plugin-runner.c 2018-02-22 18:15:57 +0000 +++ plugin-runner.c 2018-08-19 01:03:28 +0000 @@ -1093,7 +1093,12 @@ new_plugin->pid = pid; new_plugin->fd = pipefd[0]; - + + if(debug){ + fprintf(stderr, "Plugin %s started (PID %" PRIdMAX ")\n", + new_plugin->name, (intmax_t) (new_plugin->pid)); + } + /* Unblock SIGCHLD so signal handler can be run if this process has already completed */ ret = (int)TEMP_FAILURE_RETRY(sigprocmask(SIG_UNBLOCK, === modified file 'plugins.d/mandos-client.c' --- plugins.d/mandos-client.c 2018-02-22 14:34:19 +0000 +++ plugins.d/mandos-client.c 2018-08-15 09:26:02 +0000 @@ -272,6 +272,58 @@ return true; } +/* Set effective uid to 0, return errno */ +__attribute__((warn_unused_result)) +int raise_privileges(void){ + int old_errno = errno; + int ret = 0; + if(seteuid(0) == -1){ + ret = errno; + } + errno = old_errno; + return ret; +} + +/* Set effective and real user ID to 0. Return errno. */ +__attribute__((warn_unused_result)) +int raise_privileges_permanently(void){ + int old_errno = errno; + int ret = raise_privileges(); + if(ret != 0){ + errno = old_errno; + return ret; + } + if(setuid(0) == -1){ + ret = errno; + } + errno = old_errno; + return ret; +} + +/* Set effective user ID to unprivileged saved user ID */ +__attribute__((warn_unused_result)) +int lower_privileges(void){ + int old_errno = errno; + int ret = 0; + if(seteuid(uid) == -1){ + ret = errno; + } + errno = old_errno; + return ret; +} + +/* Lower privileges permanently */ +__attribute__((warn_unused_result)) +int lower_privileges_permanently(void){ + int old_errno = errno; + int ret = 0; + if(setuid(uid) == -1){ + ret = errno; + } + errno = old_errno; + return ret; +} + /* * Initialize GPGME. */ @@ -297,6 +349,56 @@ return false; } + /* Workaround for systems without a real-time clock; see also + Debian bug #894495: */ + do { + { + time_t currtime = time(NULL); + if(currtime != (time_t)-1){ + struct tm tm; + if(gmtime_r(&currtime, &tm) == NULL) { + perror_plus("gmtime_r"); + break; + } + if(tm.tm_year != 70 or tm.tm_mon != 0){ + break; + } + if(debug){ + fprintf_plus(stderr, "System clock is January 1970"); + } + } else { + if(debug){ + fprintf_plus(stderr, "System clock is invalid"); + } + } + } + struct stat keystat; + ret = fstat(fd, &keystat); + if(ret != 0){ + perror_plus("fstat"); + break; + } + ret = raise_privileges(); + if(ret != 0){ + errno = ret; + perror_plus("Failed to raise privileges"); + break; + } + if(debug){ + fprintf_plus(stderr, + "Setting system clock to key file mtime"); + } + time_t keytime = keystat.st_mtim.tv_sec; + if(stime(&keytime) != 0){ + perror_plus("stime"); + } + ret = lower_privileges(); + if(ret != 0){ + errno = ret; + perror_plus("Failed to lower privileges"); + } + } while(false); + rc = gpgme_data_new_from_fd(&pgp_data, fd); if(rc != GPG_ERR_NO_ERROR){ fprintf_plus(stderr, "bad gpgme_data_new_from_fd: %s: %s\n", @@ -310,6 +412,81 @@ gpgme_strsource(rc), gpgme_strerror(rc)); return false; } + { + gpgme_import_result_t import_result + = gpgme_op_import_result(mc->ctx); + if((import_result->imported < 1 + or import_result->not_imported > 0) + and import_result->unchanged == 0){ + fprintf_plus(stderr, "bad gpgme_op_import_results:\n"); + fprintf_plus(stderr, + "The total number of considered keys: %d\n", + import_result->considered); + fprintf_plus(stderr, + "The number of keys without user ID: %d\n", + import_result->no_user_id); + fprintf_plus(stderr, + "The total number of imported keys: %d\n", + import_result->imported); + fprintf_plus(stderr, "The number of imported RSA keys: %d\n", + import_result->imported_rsa); + fprintf_plus(stderr, "The number of unchanged keys: %d\n", + import_result->unchanged); + fprintf_plus(stderr, "The number of new user IDs: %d\n", + import_result->new_user_ids); + fprintf_plus(stderr, "The number of new sub keys: %d\n", + import_result->new_sub_keys); + fprintf_plus(stderr, "The number of new signatures: %d\n", + import_result->new_signatures); + fprintf_plus(stderr, "The number of new revocations: %d\n", + import_result->new_revocations); + fprintf_plus(stderr, + "The total number of secret keys read: %d\n", + import_result->secret_read); + fprintf_plus(stderr, + "The number of imported secret keys: %d\n", + import_result->secret_imported); + fprintf_plus(stderr, + "The number of unchanged secret keys: %d\n", + import_result->secret_unchanged); + fprintf_plus(stderr, "The number of keys not imported: %d\n", + import_result->not_imported); + for(gpgme_import_status_t import_status + = import_result->imports; + import_status != NULL; + import_status = import_status->next){ + fprintf_plus(stderr, "Import status for key: %s\n", + import_status->fpr); + if(import_status->result != GPG_ERR_NO_ERROR){ + fprintf_plus(stderr, "Import result: %s: %s\n", + gpgme_strsource(import_status->result), + gpgme_strerror(import_status->result)); + } + fprintf_plus(stderr, "Key status:\n"); + fprintf_plus(stderr, + import_status->status & GPGME_IMPORT_NEW + ? "The key was new.\n" + : "The key was not new.\n"); + fprintf_plus(stderr, + import_status->status & GPGME_IMPORT_UID + ? "The key contained new user IDs.\n" + : "The key did not contain new user IDs.\n"); + fprintf_plus(stderr, + import_status->status & GPGME_IMPORT_SIG + ? "The key contained new signatures.\n" + : "The key did not contain new signatures.\n"); + fprintf_plus(stderr, + import_status->status & GPGME_IMPORT_SUBKEY + ? "The key contained new sub keys.\n" + : "The key did not contain new sub keys.\n"); + fprintf_plus(stderr, + import_status->status & GPGME_IMPORT_SECRET + ? "The key contained a secret key.\n" + : "The key did not contain a secret key.\n"); + } + return false; + } + } ret = close(fd); if(ret == -1){ @@ -356,9 +533,8 @@ /* Create new GPGME "context" */ rc = gpgme_new(&(mc->ctx)); if(rc != GPG_ERR_NO_ERROR){ - fprintf_plus(stderr, "Mandos plugin mandos-client: " - "bad gpgme_new: %s: %s\n", gpgme_strsource(rc), - gpgme_strerror(rc)); + fprintf_plus(stderr, "bad gpgme_new: %s: %s\n", + gpgme_strsource(rc), gpgme_strerror(rc)); return false; } @@ -400,8 +576,7 @@ /* Create new empty GPGME data buffer for the plaintext */ rc = gpgme_data_new(&dh_plain); if(rc != GPG_ERR_NO_ERROR){ - fprintf_plus(stderr, "Mandos plugin mandos-client: " - "bad gpgme_data_new: %s: %s\n", + fprintf_plus(stderr, "bad gpgme_data_new: %s: %s\n", gpgme_strsource(rc), gpgme_strerror(rc)); gpgme_data_release(dh_crypto); return -1; @@ -420,24 +595,23 @@ if(result == NULL){ fprintf_plus(stderr, "gpgme_op_decrypt_result failed\n"); } else { - fprintf_plus(stderr, "Unsupported algorithm: %s\n", - result->unsupported_algorithm); - fprintf_plus(stderr, "Wrong key usage: %u\n", - result->wrong_key_usage); + if(result->unsupported_algorithm != NULL) { + fprintf_plus(stderr, "Unsupported algorithm: %s\n", + result->unsupported_algorithm); + } + fprintf_plus(stderr, "Wrong key usage: %s\n", + result->wrong_key_usage ? "Yes" : "No"); if(result->file_name != NULL){ fprintf_plus(stderr, "File name: %s\n", result->file_name); } - gpgme_recipient_t recipient; - recipient = result->recipients; - while(recipient != NULL){ + + for(gpgme_recipient_t r = result->recipients; r != NULL; + r = r->next){ fprintf_plus(stderr, "Public key algorithm: %s\n", - gpgme_pubkey_algo_name - (recipient->pubkey_algo)); - fprintf_plus(stderr, "Key ID: %s\n", recipient->keyid); + gpgme_pubkey_algo_name(r->pubkey_algo)); + fprintf_plus(stderr, "Key ID: %s\n", r->keyid); fprintf_plus(stderr, "Secret key available: %s\n", - recipient->status == GPG_ERR_NO_SECKEY - ? "No" : "Yes"); - recipient = recipient->next; + r->status == GPG_ERR_NO_SECKEY ? "No" : "Yes"); } } } @@ -822,58 +996,6 @@ static void empty_log(__attribute__((unused)) AvahiLogLevel level, __attribute__((unused)) const char *txt){} -/* Set effective uid to 0, return errno */ -__attribute__((warn_unused_result)) -int raise_privileges(void){ - int old_errno = errno; - int ret = 0; - if(seteuid(0) == -1){ - ret = errno; - } - errno = old_errno; - return ret; -} - -/* Set effective and real user ID to 0. Return errno. */ -__attribute__((warn_unused_result)) -int raise_privileges_permanently(void){ - int old_errno = errno; - int ret = raise_privileges(); - if(ret != 0){ - errno = old_errno; - return ret; - } - if(setuid(0) == -1){ - ret = errno; - } - errno = old_errno; - return ret; -} - -/* Set effective user ID to unprivileged saved user ID */ -__attribute__((warn_unused_result)) -int lower_privileges(void){ - int old_errno = errno; - int ret = 0; - if(seteuid(uid) == -1){ - ret = errno; - } - errno = old_errno; - return ret; -} - -/* Lower privileges permanently */ -__attribute__((warn_unused_result)) -int lower_privileges_permanently(void){ - int old_errno = errno; - int ret = 0; - if(setuid(uid) == -1){ - ret = errno; - } - errno = old_errno; - return ret; -} - /* Helper function to add_local_route() and delete_local_route() */ __attribute__((nonnull, warn_unused_result)) static bool add_delete_local_route(const bool add,