Mailinglist Archive: opensuse-security (359 mails)

< Previous Next >
rsync wrapper perlscript (was SCP-proxy / SFTP-proxy wanted)
  • From: Stefan Seyfried <seife@xxxxxxxxxxxxxxxx>
  • Date: Tue, 22 Jul 2003 13:45:45 +0200
  • Message-id: <20030722114545.GA8499@xxxxxxxxxxxxxxxx>
On Mon, Jul 21, 2003 at 09:15:07AM +0200, Steffen Dettmer wrote:

> You do "client push" of files for backup (instead server poll),

no, i do server poll, since my backup server accesses the clients
through a masquerading router -> no way back :-) But the wrapper
should also work for client push, just check the rsync commandline
as described below, probably you don't need to check for "--sender",
but in fact check, that it is _not_ there to prevent stealing
of your data from the backup server.

> yes? How do you do that? I found it is not so easy using rsync,
> because this likes root permissions on the backup host because
> maybe you want perserve UID and such. Having root-rsync access
> likes to limit the access to same backup-tree, at least. Does you
> perl-wrapper protects against this? I mean, the cilent can rsync
> to e.g. /.../backup/client-hostname/ as root, but not below /etc
> and such? In that case, would you share your script?

no, i completely mirror the whole machines, including /etc/, excluding
only a few directories (/proc, postgres datadir, tomcat work-dir), but
it should be easy to hack into the perlscript.
The rsync_wrapper is simple:

# rsync wrapper, borrowed from
if ( $line =~ m#^/usr/bin/rsync --server --sender # ) {
# this regexp will need tweaking to handle unusual
# (but legal) characters in paths. eg: [_\.]
($safeline=$line) =~ s|[^\w\s\d\-\/\.]||g;
if ( $line ne $safeline ) { exit 1; }
} else {
exit 1;

i put this in /root/bin/rsync_wrapper, my authorized_keys is like this:

command="bin/rsync_wrapper",no-pty,no-port-forwarding,no-agent-forwarding ssh-dss AAA...

this is all on the "client machine", the one which is backed up.
On the server, it is important to call rsync with the "--rsync-path="-Option,
otherwise, the $SSH_ORIGINAL_COMMAND will be "rsync --server --sender..." and
not "/usr/bin/rsync --server --sender..."
So you have to do (on the server) "rsync --rsync-path=/usr/bin/rsync -e ssh ..."

If you are really paranoid, just do something like
rsync -e ssh -avP --bwlimit=1 localhost:/etc /tmp/
and in another terminal search the output of "ps auxwwf" for the exact
command-line which is executed via ssh on the client, then you can put
that command into authorized_keys or check especially against it in the
wrapper. In my example, it was
rsync --server --sender -vlogDtpr --bwlimit=1 --partial . /etc
so you can check if only the paths you want to allow are at the end of the

This script is not my invention, as stated in the comment.
Stefan Seyfried

Senior Consultant community4you GmbH, Chemnitz, Germany.

< Previous Next >
Follow Ups