I'm using freeIPA to define RBAC, HBAC and sudo
rules, as well as SELinux user mappings for a domain of a couple hundred virtual machines, where I need to grant different levels of access to several teams (developers, database administrators, system administrators, management, ...).
Currently, the SELinux policy on these machines is set to targeted
, and I'm pondering the possibility of deleting the unconfined_u
SELinux user in order to make these systems run under a strict
policy.
In order to do that, one of the requirements is to make transparent to the end user the fact that he/she has been 'demoted' from unconfined_u
to staff_u
. The problem resides in the way sudo
interoperates with the SELinux user mappings. Some facts:
if you want to use a confined SELinux user and you want to still be able to use
sudo
, you need to usestaff_u
, as this is the SELinux user with access to SETUID executables.when a user logs into a system, he/she is assigned a SELinux user mapping. That mapping does not change even in the case the SELinux user can run
su
(unconfined_u
) orsudo
(unconfined_u
,staff_u
).the
SELinux Spec
forsudo
currently contains facilities to run commands in definedtypes
androles
, but lacks the possibility of specifying theuser
too. Further reference can be found here.the machines involved in this deployment are all freeIPA clients and their
sudo
policies are managed by freeIPA, but they also have apuppet
managed, customized/etc/sudoers
file, provided as a fallback in case of a freeIPA failure.
My first attempt to solve this problem involved witting a policy module containing the needed rules to allow staff_u
access to the unmodified sudorules
. This approach has proven to be wrong, because the policy can grow indefinitely and finally what you are doing is punching a hole in the policy.
So the way I have dealt with this these facts so far has been rewriting the sudorules
to explicitly contain a call to runcon
to switch to the appropriate SELinux user, so a typical developer now needs to run, for example:
$ sudo -u jboss runcon -u sysadm_u jboss_cli.sh
This has the drawback of having to modify all the existing sudorules
and forcing the user to change the way the usually run stuff. So the questions are:
- is there a way to explicitly define the SELinux user in a
Runas_Spec
definition? - if not possible via
sudoers
, is it possible to define, or otherwise bind, asudorule
to a SELinux user mapping in freeIPA?
Consider this scenario:
# ipa sudorule-show services_4_operators_3
Rule name: services_4_operators_3
Description: Operator Level 3 access to service management commands
Enabled: TRUE
User Groups: operators_3
Host Groups: all-hosts
Sudo Allow Command Groups: services
Sudo Option: type=sysadm_t, role=sysadm_r
# ipa sudocmdgroup-show services
Sudo Command Group: services
Description: commands for services and daemons management
Member Sudo commands: /sbin/service, /sbin/chkconfig
If I try:
$ sudo service sshd status
sudo: unable to open /var/log/sudo-io/seq: Permission denied
time->Wed Sep 11 09:57:30 2013 type=PATH msg=audit(1378886250.584:46644668): item=0 name="/var/log/sudo-io/seq" inode=154 dev=fd:0c mode=0100600 ouid=0 ogid=1168000009 rdev=00:00 obj=unconfined_u:object_r:var_log_t:s0 type=CWD msg=audit(1378886250.584:46644668): cwd="/home/some_user" type=SYSCALL msg=audit(1378886250.584:46644668): arch=c000003e syscall=2 success=no exit=-13 a0=7fff2e7ab970 a1=42 a2=180 a3=0 items=1 ppid=2374 pid=2442 auid=1168000009 uid=1168000009 gid=1168000009 euid=0 suid=0 fsuid=0 egid=1168000009 sgid=1168000009 fsgid=1168000009 tty=pts0 ses=6459 comm="sudo" exe="/usr/bin/sudo" subj=staff_u:staff_r:staff_sudo_t:s0-s0:c0.c1023 key="access" type=AVC msg=audit(1378886250.584:46644668): avc: denied { read write } for pid=2442 comm="sudo" name="seq" dev=dm-12 ino=154 scontext=staff_u:staff_r:staff_sudo_t:s0-s0:c0.c1023 tcontext=unconfined_u:object_r:var_log_t:s0 tclass=file
Because I'm using log_output
in Defaults
and:
# ll -dZ /var/log/sudo-io
drwx------. root root system_u:object_r:var_log_t:s0 /var/log/sudo-io/
Trying to "fix" this AVC denial will result in the aforementioned infinite policy module, because allowing:
allow staff_sudo_t var_log_t:file { open read write lock create };
allow staff_sudo_t var_log_t:dir { write add_name create search };
is a spurious problem, as shown when enabling such permissions:
$ sudo service sshd status
env: /etc/init.d/sshd: Permission denied
time->Wed Sep 11 11:00:53 2013 type=PATH msg=audit(1378890053.185:46646934): item=0 name="/etc/init.d/sshd" inode=5490 dev=fd:01 mode=0100755 ouid=0 ogid=0 rdev=00:00 obj=system_u:object_r:sshd_initrc_exec_t:s0 type=CWD msg=audit(1378890053.185:46646934): cwd="/" type=SYSCALL msg=audit(1378890053.185:46646934): arch=c000003e syscall=59 success=no exit=-13 a0=7fffc0829862 a1=7fffc0829578 a2=607030 a3=ffffe000 items=1 ppid=6715 pid=6720 auid=1168000009 uid=0 gid=0 euid=0 suid=0 fsuid=0 egid=0 sgid=0 fsgid=0 tty=pts2 ses=6459 comm="env" exe="/bin/env" subj=staff_u:sysadm_r:sysadm_t:s0-s0:c0.c1023 key=(null) type=AVC msg=audit(1378890053.185:46646934): avc: denied { execute } for pid=6720 comm="env" name="sshd" dev=dm-1 ino=5490 scontext=staff_u:sysadm_r:sysadm_t:s0-s0:c0.c1023 tcontext=system_u:object_r:sshd_initrc_exec_t:s0 tclass=file
FINAL EDIT
I have finally adopted a mid-term solution. I have configured my IPA server as follows:
$ sudo -u dsastrem ipa config-show
Maximum username length: 32
Home directory base: /home
Default shell: /bin/rbash
Default users group: ipausers
Default e-mail domain: company.com
Search time limit: 2
Search size limit: 100
User search fields: uid,givenname,sn,telephonenumber,ou,title
Group search fields: cn,description
Enable migration mode: FALSE
Certificate Subject base: O=COMPANY.COM
Password Expiration Notification (days): 4
Password plugin features: AllowNThash
SELinux user map order: guest_u:s0$xguest_u:s0$user_u:s0$staff_u:s0-s0:c0.c1023$unconfined_u:s0-s0:c0.c1023
Default SELinux user: guest_u:s0
Default PAC types: MS-PAC
and I have defined some SELinux user mappings similar to this one that bind some RBACs to a SELinux user (staff_u
).
$ sudo -u dsastrem ipa selinuxusermap-find
---------------------------
X SELinux User Maps matched
---------------------------
....
Rule name: semap_operators_3_mad
SELinux User: staff_u:s0-s0:c0.c1023
HBAC Rule: operators_3_access
Description: SELinux user mapping for MAD level 3 operators
Enabled: TRUE
....
----------------------------
Number of entries returned X
----------------------------
My sudo
rules now look like this one:
Rule name: services_4_operators_3
Description: Operator Level 3 access to service management commands
Enabled: TRUE
User Groups: operators_3
Host Groups: all-hosts
Sudo Allow Command Groups: services
Sudo Option: role=unconfined_r
This is not my final goal, as I wanted to completely eliminate unconfined_u
, but it's a good step forward, as it enhances a little bit the overall security. Of course, Matthew's answer is correct, as staff_u
should be able to transition to a higher privileged domain via sudo
options; but there's still the problem of system_u
not being completely equipped to replace unconfined_u
. Maybe because it is not intended to do so.
You are aware that you can move into the
sysadm_r
role asstaff_u
right?For example, the following below would work.
This will allow you to do (almost) what you can do as root as unconfined.
Oh and one final tip. Using
su
is a bit tricky with RBAC (it does a lot of stuff which gets it into all sorts of places). Instead you can use therunuser
command which does the same thing without a lot ofsu
overheads.I actually restrict
su
use in sudoers like so;Because by default the SELinux policy doesn't allow the
sudo
transition to manage the necessary signals. Really people should probably just usesudo -i
anyway.I normally hardlink
runuser
toru
as a two-letter replacement for people who prefer to runsudo su -
out of a bad habit (like me!).