rsync and selinux – opendir failed: Permission denied

Selinux could sometime mess up with your setup. Let’s say you configured your rsync daemon but still, you get the error related to permissions when executing the rsync to copy files!

rsync: opendir "/." (in backup2) failed: Permission denied (13)

Apparently, the rsync client connects to the server and it finds there is a section name “backup2”, but still no permission despite you explicitly set in the section uid and ig to be root (uid=0 and gid=0 in the section)!

The most common reason is

selinux denies rsync process to open the directory exported by the path in your rsync configuration file.

By default, Selinux will deny access to any of the files and directories in your system! In most cases here what can you help:

setsebool -P rsync_export_all_ro=1

rsync_export_all_ro will export any files and directories read-only and requests like above will not be denied.
The capital letter “-P” is to set it permanently for the system over reboots.

In rear cases you can use additional Selinux variables related to rsync:

[root@srv ~]# getsebool -a|grep rsync
postgresql_can_rsync --> off
rsync_anon_write --> off
rsync_client --> off
rsync_export_all_ro --> off
rsync_full_access --> off

They are almost self-explanatory. write access is used only if you want to push data to the server, so it is not necessary if you just want to copy files from your server. You might have more variables if you have installed more ruleset files (they will be installed automatically if you install more programs, which could have an influence on rsync like nfs and so on).

Even enabling above Selinux variables you still could get file access permissions denied for some special devices in /dev directory there are two more options:

  1. so you could just temporary “disable” Selinux (in fact it is not disabled, but set to permissive mode – the incidents are only reported not denied), do your job and get back to normal mode (Enforcing – denying on incidents):
    [root@srv ~]# getenforce 
    Enforcing
    

    This says you are definitely using Selinux!
    Set to permissive mode

    [root@srv ~]# setenforce 0
    [root@srv ~]# getenforce 
    Permissive
    

    Do your job here like execute rsync on the remote computer and wait for it to finish copying files. And then return the “Enforcing” mode again to be protected:

    [root@srv ~]# setenforce 1
    [root@srv ~]# getenforce 
    Enforcing
    

    “getenforce” is used only to get the current state and verify we change between modes, it is not mandatory to be used when using “setenforce”.

  2. Search for the rsync incidents in audit log with “ausearch”, make a custom selinux module and load it to take into effect

    [root@srv ~]# ausearch -c ‘rsync’ –raw | audit2allow

    #============= rsync_t ==============
    allow rsync_t default_t:blk_file getattr;
    allow rsync_t default_t:chr_file getattr;

    #!!!! This avc is allowed in the current policy
    allow rsync_t default_t:dir read;

    #!!!! This avc can be allowed using the boolean ‘rsync_full_access’
    allow rsync_t default_t:fifo_file getattr;

    #!!!! This avc is allowed in the current policy
    allow rsync_t default_t:file { getattr open read };

    #!!!! This avc is allowed in the current policy
    allow rsync_t default_t:lnk_file { getattr read };

    #!!!! This avc can be allowed using the boolean ‘rsync_full_access’
    allow rsync_t default_t:sock_file getattr;

    root@srv ~]# ausearch -c ‘rsync’ –raw | audit2allow -M rsync-module
    ******************** IMPORTANT ***********************
    To make this policy package active, execute:

    semodule -i rsync-module.pp

    root@srv ~]# semodule -i rsync-module.pp
    root@srv ~]#

    Your module will be loaded and rsync will have proper permissions.

Bonus

Here is the whole output of the rsync command:

[root@dev ~]# rsync --partial --verbose --progress --stats --recursive --times --perms --links --owner --group --hard-links --devices srv-remote-ip::backup2 /mnt/backup2/
receiving incremental file list
rsync: opendir "/." (in backup2) failed: Permission denied (13)
./

Number of files: 1 (dir: 1)
Number of created files: 0
Number of deleted files: 0
Number of regular files transferred: 0
Total file size: 0 bytes
Total transferred file size: 0 bytes
Literal data: 0 bytes
Matched data: 0 bytes
File list size: 97
File list generation time: 0.001 seconds
File list transfer time: 0.000 seconds
Total bytes sent: 27
Total bytes received: 115

sent 27 bytes  received 115 bytes  94.67 bytes/sec
total size is 0  speedup is 0.00
rsync error: some files/attrs were not transferred (see previous errors) (code 23) at main.c(1659) [generator=3.1.3]

And here is what you can find in the audit file log. As you can see read, getattr are forbidden to rsync server process!

[root@dev ~]# ausearch -c 'rsync' --raw
type=AVC msg=audit(1551255571.733:577370): avc:  denied  { read } for  pid=27410 comm="rsync" name="mytv-mirror" dev="md2" ino=1310723 scontext=system_u:system_r:rsync_t:s0 tcontext=unconfined_u:object_r:default_t:s0 tclass=dir
type=SYSCALL msg=audit(1551255571.733:577370): arch=c000003e syscall=257 success=no exit=-13 a0=ffffffffffffff9c a1=7ffc515e3120 a2=90800 a3=0 items=0 ppid=27406 pid=27410 auid=4294967295 uid=0 gid=0 euid=0 suid=0 fsuid=0 egid=0 sgid=0 fsgid=0 tty=(none) ses=4294967295 comm="rsync" exe="/usr/bin/rsync" subj=system_u:system_r:rsync_t:s0 key=(null)
type=PROCTITLE msg=audit(1551255571.733:577370): proctitle=2F7573722F62696E2F7273796E63002D2D6461656D6F6E002D2D6E6F2D646574616368
type=AVC msg=audit(1551255587.644:577374): avc:  denied  { getattr } for  pid=27412 comm="rsync" path="/config" dev="md2" ino=1311131 scontext=system_u:system_r:rsync_t:s0 tcontext=unconfined_u:object_r:default_t:s0 tclass=file
type=SYSCALL msg=audit(1551255587.644:577374): arch=c000003e syscall=6 success=yes exit=0 a0=7ffc515dedd0 a1=7ffc515ded40 a2=7ffc515ded40 a3=0 items=0 ppid=27406 pid=27412 auid=4294967295 uid=0 gid=0 euid=0 suid=0 fsuid=0 egid=0 sgid=0 fsgid=0 tty=(none) ses=4294967295 comm="rsync" exe="/usr/bin/rsync" subj=system_u:system_r:rsync_t:s0 key=(null)
type=PROCTITLE msg=audit(1551255587.644:577374): proctitle=2F7573722F62696E2F7273796E63002D2D6461656D6F6E002D2D6E6F2D646574616368
type=AVC msg=audit(1551255587.644:577373): avc:  denied  { read } for  pid=27412 comm="rsync" name="mytv-mirror" dev="md2" ino=1310723 scontext=system_u:system_r:rsync_t:s0 tcontext=unconfined_u:object_r:default_t:s0 tclass=dir
type=SYSCALL msg=audit(1551255587.644:577373): arch=c000003e syscall=257 success=yes exit=4 a0=ffffffffffffff9c a1=7ffc515e3120 a2=90800 a3=0 items=0 ppid=27406 pid=27412 auid=4294967295 uid=0 gid=0 euid=0 suid=0 fsuid=0 egid=0 sgid=0 fsgid=0 tty=(none) ses=4294967295 comm="rsync" exe="/usr/bin/rsync" subj=system_u:system_r:rsync_t:s0 key=(null)
type=PROCTITLE msg=audit(1551255587.644:577373): proctitle=2F7573722F62696E2F7273796E63002D2D6461656D6F6E002D2D6E6F2D646574616368
type=AVC msg=audit(1551255587.644:577375): avc:  denied  { getattr } for  pid=27412 comm="rsync" path="/rootfs.dev" dev="md2" ino=1310724 scontext=system_u:system_r:rsync_t:s0 tcontext=unconfined_u:object_r:default_t:s0 tclass=lnk_file
type=SYSCALL msg=audit(1551255587.644:577375): arch=c000003e syscall=6 success=yes exit=0 a0=7ffc515dedd0 a1=7ffc515ded40 a2=7ffc515ded40 a3=0 items=0 ppid=27406 pid=27412 auid=4294967295 uid=0 gid=0 euid=0 suid=0 fsuid=0 egid=0 sgid=0 fsgid=0 tty=(none) ses=4294967295 comm="rsync" exe="/usr/bin/rsync" subj=system_u:system_r:rsync_t:s0 key=(null)
type=PROCTITLE msg=audit(1551255587.644:577375): proctitle=2F7573722F62696E2F7273796E63002D2D6461656D6F6E002D2D6E6F2D646574616368
type=AVC msg=audit(1551255587.644:577376): avc:  denied  { read } for  pid=27412 comm="rsync" name="rootfs.dev" dev="md2" ino=1310724 scontext=system_u:system_r:rsync_t:s0 tcontext=unconfined_u:object_r:default_t:s0 tclass=lnk_file
type=SYSCALL msg=audit(1551255587.644:577376): arch=c000003e syscall=89 success=yes exit=38 a0=7ffc515dedd0 a1=7ffc515dfdd0 a2=fff a3=0 items=0 ppid=27406 pid=27412 auid=4294967295 uid=0 gid=0 euid=0 suid=0 fsuid=0 egid=0 sgid=0 fsgid=0 tty=(none) ses=4294967295 comm="rsync" exe="/usr/bin/rsync" subj=system_u:system_r:rsync_t:s0 key=(null)
type=PROCTITLE msg=audit(1551255587.644:577376): proctitle=2F7573722F62696E2F7273796E63002D2D6461656D6F6E002D2D6E6F2D646574616368
type=AVC msg=audit(1551255587.647:577377): avc:  denied  { getattr } for  pid=27412 comm="rsync" path="/rootfs/dev/vcsa" dev="md2" ino=1312743 scontext=system_u:system_r:rsync_t:s0 tcontext=unconfined_u:object_r:default_t:s0 tclass=chr_file

Bonus 2

This command “audit2allow” is provided by policycoreutils-python package in CentOS 7 and by default it might be missing.

yum install -y policycoreutils-python

Leave a Reply

Your email address will not be published. Required fields are marked *