4

I'm trying to write a bash script that will execute rsync when called by pam_exec. I've tried a couple different ways, and I'm not sure what I'm doing wrong. When I try to run the script at login by adding

session     optional      pam_exec.so /usr/bin/local/sync.sh

to my sshd file, it gives me an exit code of 12.

If I log in and then manually run my script, it allows me to connect to the remote server, and it lists my files, but it doesn't actually sync anything.

I have tried the code below using buth $USER and $PAM_USER. $PAM_USER doesn't work at all.

#!/bin/sh 
rsync -azv -e ssh $USER@remote_server:/home/html/$USER/ /home/html/$USER
0

1 Answer 1

2

The man page for pam_exec explains that the module provides $PAM_USER, not $USER:

the following PAM items are exported as environment variables: PAM_RHOST, PAM_RUSER, PAM_SERVICE, PAM_TTY, PAM_USER and PAM_TYPE [...]

On my Debian based system I added this line just before the entry for pam_motd

# Run a script on login
session    optional     pam_exec.so /usr/local/etc/pam_exec.sh

I then created the test script, remembering to make it executable:

cat >/usr/local/etc/pam_exec.sh <<'EOF'; chmod a+rx /usr/local/etc/pam_exec.sh
#!/bin/bash
#
test open_session = "$PAM_TYPE" && {
    echo
    date
    echo "PAM_USER=$PAM_USER, USER=$USER."

} >>/tmp/pam_exec.log

exit 0
EOF

Finally, I opened a new login session to my test system, and saw that on session start I received information such as this in my log file /tmp/pam_exec.log:

Mon Nov  9 23:32:52 GMT 2015
PAM_USER=roaima, USER=.

To implement your requirement you would need to use a script something like this:

#!/bin/sh
rsync -azq -e ssh "$PAM_USER"@remote_server:/home/html/"$PAM_USER"/ /home/html/"$PAM_USER" >/dev/null 2>&1

Notice that all output from rsync is discarded. This is necessary to ensure that client/server applications using ssh as a transport do not get hit by unexpected output before they can start their negotiation. If you really want to present it to the user, I would recommend you write it to a user-specific log file such as "$HOME/.pam_exec.log" and then use a line like this in the user's .profile to output it after the login process has completed:

if test -t 1 -a -s "$HOME/.pam_exec.log"
then
    echo "Prelogin results"
    sed 's/^/| /' "$HOME/.pam_exec.log"
fi

It's not immune to a race condition, but IME most users don't login simultaneously multiple times to the same server. If you find this scenario is common there are ways to deal with it.

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .