miller the gorilla
miller the gorilla

Reputation: 920

ssmtp called from a script fails with ssmtp: Cannot open mailhub:25 but script is running with user in mail group

I am trying to get motion to run a script on the on_movie_end event. The script, below, calls ssmtp to send the file as an attachment. If I call the file from the command line, as the normal user, or using sudo -u, the script runs fine, with no complaints.

The motion process is running as the user motion, having been started with a systemd unit the exec line being: `ExecStart= (bash test for variable ellipted) ... exec /usr/bin/motion -n'

The script that runs on_movie_end is below :

#!/bin/bash
echo "I AM HERE!!! $(id) $(id -u) $(groups)" >> /var/log/motion.log
INFILE="$(find /var/lib/motion/files/ -type f -printf "%t %p\n" | sort -n | tail -1 | awk 'NR==1,NR==7 {print $6}')"
FILENAME="${1}$(date +%j-%m-%T).mkv"
CHECKSUM=$(sha256sum ${INFILE})
echo -e "New Motion event for ${CHECKSUM} from Camera 1" | (cat - && uuencode ${INFILE} "${FILENAME}") | ssmtp [email protected]

the log prints out the following (from the first line):

I AM HERE!!! uid=978(motion) gid=39(video) groups=39(video),8(mail) context=system_u:system_r:initrc_t:s0 978 video mail

my script permissions are:

-r-xr-x---. 1 motion video unconfined_u:object_r:var_lib_t:s0 410 Mar 19 18:50 /var/lib/motion/script.sh

the error that is reported in journalctl -f is :

Mar 19 18:29:48 localhost.localdomain sSMTP[1675]: /etc/ssmtp/ssmtp.conf not found
Mar 19 18:29:51 localhost.localdomain sSMTP[1675]: Unable to locate mailhub
Mar 19 18:29:51 localhost.localdomain audit[1675]: AVC avc:  denied  { append } dead letter>
Mar 19 18:29:51 localhost.localdomain audit[1675]: SYSCALL arch=c00000b7 syscal>
Mar 19 18:29:51 localhost.localdomain sSMTP[1675]: Cannot open mailhub:25
Mar 19 18:29:51 localhost.localdomain sh[1675]: ssmtp: Cannot open mailhub:25

my permissions for /etc/ssmtp/ssmtp.conf are:

ls -alZ /etc/ssmtp
total 20
drwxr-sr-x.  2 root mail system_u:object_r:etc_t:s0   42 Mar 19 19:51 .
drwxr-xr-x. 95 root root system_u:object_r:etc_t:s0 8192 Mar 19 17:55 ..
-rw-r--r--.  1 root root system_u:object_r:etc_t:s0  255 Mar 19 17:42 revaliases
-rw-r-----.  1 root mail system_u:object_r:etc_t:s0 1590 Mar 19 19:31 ssmtp.conf

I have found one forum question that looks similar to mine, in which the issue was solved by placing adding nobody to the ssmtp group, but that looks entirely sketchy, I think. [https://bbs.archlinux.org/viewtopic.php?pid=1538597#p1538597]

Here is my /etc/systemd/system/motion.service (a copy of that from motion github, slightly edited).

#
# This systemd unit file is part of the motion project:
#
# https://motion-project.github.io/
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of version 2 of the GNU General Public License as
# published by the Free Software Foundation.
#
# This program 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 Lesser General Public
# License along with this program.  If not, see
# <https://www.gnu.org/licenses/old-licenses/gpl-2.0.html>
#

[Unit]
Description=Motion - monitor live video, trigger responses, record video/stills.
Documentation=man:motion(1)
After=local-fs.target network.target

[Service]
User=motion
EnvironmentFile=-/etc/default/motion
# The the sleep on the following line is needed with systemd version
# 232, otherwise the error message that we echo doesn't hit 'systemctl
# status'.
ExecStart=/bin/sh -c '([ -r "/etc/default/motion" ] && [ "x$start_motion_daemon" != "xyes" ]) && echo "Not starting motion because start_motion_daemon=$start_motion_daemon - check /etc/default/motion" && sleep 1 && exit 78 ; exec /usr/bin/motion -n'
Type=simple
# Set StandardError=journal to use journald to log messages from motion.
# See also the "log_file" config file option in motion(1) and
# systemd.service(5).
StandardError=journal
ExecReload=/usr/bin/kill -s HUP $MAINPID
Restart=on-failure
RestartSec=5
# Don't restart if unconfigured / misconfigured  e.g. daemon disabled
# in defaults file.  See also /usr/include/sysexits.h or sysexits(3)
RestartPreventExitStatus=78
# To tune restart behaviour, see systemd.unit(5) and use
# "systemctl edit motion" to change the following settings:
#StartLimitBurst=
#StartLimitIntervalSec=
#StartLimitAction=
#FailureAction=
# The following can be used to increase the security of the
# installation, by mitigating risk from attacks on motion and the
# binaries, libraries and scripts which it relies on.  They are disabled
# by default in case they break existing installations, e.g. those which
# call site-local scripts which would inherit the same restrictions.
#
# See systemd.exec(5) and
# http://0pointer.net/public/systemd-nluug-2014.pdf for more details
# of these and other related options.
#
# Use "systemctl edit motion" to change these settings.
#PrivateTmp=true
#NoNewPrivileges=yes
#PrivateNetwork=yes
#ProtectHome=tmpfs
#DeviceAllow=/dev/video0
#MountFlags=private
# SystemCallFilter=

[Install]
WantedBy=multi-user.target

I can run the script from the command line as the user or as motion, the systemd user, and the owner of the motion process when the script is run, thus the owner of the script, but the systemd run process only sends mail when the permissions of smtp.conf are set to 0644, which is world accessible, so I cannot do it.

I don't think that it is an selinux issue as the same problem occurs when selinux is set to permissive, but perhaps the selinux initrc_t on the script should be initrc_exec_t

What to do? Any hints gratefully accepted.... :)

Upvotes: 0

Views: 364

Answers (1)

miller the gorilla
miller the gorilla

Reputation: 920

Ok, I figured out an answer, and it turned out that I was using a non-standard location for the script, so the selinux context was preventing it from running, even when selinux was in permissive mode.

I moved the script to /usr/local/sbin, and ran restorecon -r /usr/local/sbin and this allowed the script to run.

Upvotes: 0

Related Questions