In Part 1 of this series, we discussed the basics of host security through traditional security mechanisms (DAC) and newer efficient mechanisms (MAC). We also understood that the right combination of both the Access Control Methods eventually leads to an effective security policy that can be applied to any host.
We learnt that applying security to an operating system as a whole was far more practical and efficient than applying security to each individual application running on the operating system, and that SELinux was one such mechanism. SELinux achieves MAC objectives by applying a ‘Security Context’ to subjects and objects, and by controlling access of subjects to objects based on access control rules.
In Part I, we also learnt to enable SELinux on Red Hat Enterprise Linux. The steps are briefly summarised below:
- Edit
/etc/sysconfig/selinux
and make sure it contains the lines:SELINUX=permissive SELINUXTYPE=targeted
- Reboot and check.
In this article, we will explore Permissive and Reboot and check. Enforcing Modes. We will also learn a few SELinux commands that will help in understanding SELinux policies better.
Understanding SELinux modes
Irrespective of the policy or the rules implemented through SELinux Type Enforcement, there are three modes of operation for SELinux:
- Disabled
- Permissive
- Enforcing
Disabled mode implies that SELinux is disabled and not implemented on the host. This has been the most common choice in installations seen by me. Hopefully, by the end of this series, we shall be able to bring about a change in that practice by encouraging more system administrators to adopt SELinux.
Permissive mode is similar to Debugging Mode. In Permissive Mode, SELinux policies and rules are applied to subjects and objects, but actions (for example, Access Control denials) are not effected. The biggest advantage of Permissive Mode is that log files and error messages are generated based on the SELinux policy implemented.
In other words, if the SELinux policy would prevent the httpd
subject (Apache Web server) from accessing the object folder /webdata
on my system, implementing SELinux in Permissive Mode would let the Apache Web server access the folder /webdata
but log a denial in the log files.
This error logging informs the system administrator that if SELinux is activated in the Enforcing Mode, the httpd subject would be disallowed access to the /webdata folder on my system.
Permissive Mode is the initiating point for all those wanting to explore the world of Type Enforcement through SELinux. Without blocking access to your favourite programs such as OpenOffice.org, Evolution, etc, it provides you with enough debugging information to fine tune your policy before deploying it on your system.
Enforcing Mode, as the name signifies, is SELinux in action. All production systems, when hardened, should enable SELinux in Enforcing Mode. SELinux through Access Controls does have a minor performance overhead, but compared to the advantages that it brings to the table, I am sure it will soon become the norm to implement SELinux on production servers.
Controlling SELinux
The getenforce
command gets the current mode of SELinux. It reports whether SELinux is Enforcing, Permissive, or Disabled.On a system with SELinux disabled, it will display the following:
[root@station20 ~]# getenforce Disabled
On a system with SELinux in Permissive Mode, it will display:
[root@vbg ~]# getenforce Permissive
On a system with SELinux in Enforcing Mode, the following will be displayed:
[root@vbg ~]# getenforce Enforcing
setenforce
modifies the mode SELinux is running in. It is used to toggle between Permissive and Enforcing mode when SELinux is enabled.
To activate “Enforcing mode” on an SELinux-enabled system, run:
[root@vbg ~]# setenforce 1
To check the current status, use getenforce
. To activate Permissive SELinux mode, execute:
[root@vbg ~]# setenforce 0
The sestatus
command is used to get the status of a system running SELinux. Apart from mentioning the current mode of SELinux, it gives more information about the SELinux policy.
On a system with SElinux disabled, it will display:
[root@station20 ~]# sestatus SELinux status: disabled
On a System with SELinux in Permissive Mode, it will display:
[root@vbg ~]# sestatus SELinux status: enabled SELinuxfs mount: /selinux Current mode: permissive Mode from config file: permissive Policy version: 21 Policy from config file: targeted
The first line informs us that SELinux is enabled in this system.
The second line is of great significance. It displays the mount point of the SELinux pseudo file system. This file system is quite like the proc and sys file systems, and contains run-time information about your SELinux mode and various other things.
You can change run-time parameters of the SELinux system by directly writing to the files in this pseudo file system. As an example, just issue this command as the root user:
[root@vbg ~]# echo 1 > /selinux/enforce
You will see that the mode of SELinux has changed from Permissive to Enforcing.
To return back to Permissive Mode, you can run either of the commands:
[root@vbg ~]# echo 0 > /selinux/enforce
or
[root@vbg ~]# setenforce 0
The third line mentions the current SELinux mode, whereas the fourth line mentions the SELinux mode under which the system booted.
The fifth line mentions the version number of the policy (we will come to this later in this series) and finally, the sixth line mentions the Policy loaded from the configuration file (/etc/sysconfig/selinux
) at boot time.
Understanding various types of policies
By definition, an SELinux policy is a collection of rules for SELinux Mandatory Access Controls. Each one of us can make a policy to suit our needs much like we define firewall rules through iptables
. There can be no standard policy that can apply to all situations.
By default, there are two policies shipped along with Red Hat Enterprise Linux: Targeted and Strict.
The Targeted Policy is the first step in assisting system administrators to understand and implement SELinux. It only ‘targets’ certain network daemons such as the Apache Web server, FTP server, BIND DNS server and a few others, while leaving the vast majority of end-user applications largely untouched. It creates an ‘unconfined’ domain ‘confinement’ (interesting paradox, isn’t it?) and does not apply Access Control Restrictions to most applications in the unconfined domain.
This allows sysadmins to concentrate on the really vulnerable network applications and services while not interfering with their daily tasks.
Once the nuts and bolts of SELinux are clear to administrators, they should move forward towards implementing the SELinux Strict Policy.
The Strict Policy, on the other hand, is a true restrictive Access Control Policy. Before implementing this policy, make sure you understand SELinux concepts and policies well.
Under the hood of Targeted Policy
To understand any SELinux policy, use the informative command—seinfo
.
[root@vbg ~]# seinfo Statistics for policy file: /etc/selinux/targeted/policy/policy.21 Policy Version & Type: v.21 (binary, MLS) Classes: 61 Permissions: 220 Types: 1513 Attributes: 148 Users: 3 Roles: 6 Booleans: 210 Cond. Expr.: 186 Sensitivities: 1 Categories: 1024 Allow: 82518 Neverallow: 0 Auditallow: 28 Dontaudit: 5086 Role allow: 5 Role trans: 0 Type_trans: 1398 Type_change: 17 Type_member: 0 Range_trans: 23 Constraints: 47 Validatetrans: 0 Fs_use: 15 Genfscon: 64 Portcon: 264 Netifcon: 0 Nodecon: 8 Initial SIDs: 27
seinfo
is a policy query tool that queries policy files and provides vital information about it. When executed without any arguments, it queries the default loaded policy file.
As you can see the policy file read by the seinfo
tool by default is /etc/selinux/targeted/policy/policy.21
. Installed by the selinux-policy-targeted
RPM, this file contains the binary Targeted Policy.
The second line of the above output mentions that this is a binary policy with MLS (Multi Level Security). We will come to MLS in the later part of this series.
Now comes the interesting part of the output. You can clearly see various components of the policy. We will discuss these components in the course of these articles. Let us concentrate on a few important ones right now.
A typical security context as we discussed in Part 1 of this series, is of the type:
User Identity:Role:Type/Domain
As we can see from the above, in the default SELinux Targeted policy, there are:
- Users (3 in number)
- Roles (6 in number)
- Types (1,513 in number)
This means that any object or subject in the SELinux Policy installed in the system can have one of three user identities, one of six roles and one of the available 1,513 types.
To list user identities defined in the SELinux Targeted Policy, run the following command:
[root@vbg ~]# seinfo -u Users: 3 system_u root user_u
Do check all possible security contexts for objects (files, dirs, etc) and subjects (processes) in your system. The user identitity component of the Security context will have one of the above three identities and nothing else.
Similarly, to check the available roles, use the following code:
[root@vbg ~]# seinfo -r Roles: 6 staff_r user_r object_r secadm_r sysadm_r system_r
And please check the available list of types yourself by using the command given below:
[root@vbg ~]# seinfo -t
Thus we now know that any existing object or subject in the system will have a security context created out of these three users, six roles and 1,513 types.
You can alter the security context of any object by using the chcon command.
To change the type of an object, use chcon -t
. To change the user identity, use chcon -u
and chcon -r
for role.
To test the above, create an empty file “context” in the /tmp
directory and check its default security context:
[root@vbg ~]# touch /tmp/context [root@vbg ~]# ls -lZ /tmp/context -rw-r--r-- root root user_u:object_r:tmp_t:s0 /tmp/context
To change the type of this object from tmp_t
to unconfined_t
, use the code below:
[root@vbg ~]# chcon -t unconfined_t /tmp/context [root@vbg ~]# ls -Z /tmp/context -rw-r--r-- root root root:object_r:unconfined_t:s0 /tmp/context
I leave it as an exercise for you to change the role and the user for this object. If you face any issues, feel free to contact me at the e-mail ID provided below.
Assuming that, as above, you have changed the security context of an object quite a few times and you would like to revert back to the original/default security context, restorecon
comes to the rescue.
restorecon
restores files to their default security contexts. The verbose option of the restorecon
command also displays the changes made in the security context. To check the usage of this very handy command, look at the example below:
[root@vbg ~]# touch /home/vbg/test-context [root@vbg ~]# ls -Z /home/vbg/test-context -rw-rw-r-- vbg vbg user_u:object_r:user_home_t:s0 /home/vbg/test-context [root@vbg ~]# chcon -t tmp_t /home/vbg/test-context [root@vbg ~]# ls -Z /home/vbg/test-context -rw-rw-r-- vbg vbg user_u:object_r:tmp_t:s0 /home/vbg/test-context [root@vbg ~]# restorecon -v /home/vbg/test-context restorecon reset /home/vbg/test-context context user_u:object_r:tmp_t:s0->user_u:object_r:user_home_t:s0 [root@vbg ~]# ls -Z /home/vbg/test-context -rw-rw-r-- vbg vbg user_u:object_r:user_home_t:s0 /home/vbg/test-context
The above snippet shows the utility of the restorecon
command. It reads the default contexts to be applied from the policy files and applies the default security context to a file/directory object.
A word of caution when using restorecon
: DO NOT use the command with the -r
(recursive) option. It may overwrite the security contexts of some important files in the system that you may have changed.
If you think that you have spoilt the security contexts of the files in your system beyond recovery, do not panic. Help is available in the form of Auto-Relabel, at boot. Simply create an empty file /.autorelabel
. Please note that it is a hidden file.
[root@vbg ~]# touch /.autorelabel [root@vbg ~]# reboot
Following the procedure mentioned above will cause SELinux to relabel the files on your system upon rebooting. Please use this to fix any improper security context on files and directories.
You can also use the fixfiles
command to achieve the above. fixfiles
can prevent you from rebooting your system but may not be as effective. Depending on the options and time available, you can choose any option that suits you—though I would suggest the reboot option.
Still to come
So, that’s about it for now. I’ll be back the following months with topics such as:
- Understanding the Targeted Policy – Part II
- Policy Modules
- MLS and MCS
hello
this is great tutorial about se_linux
but i want to know where can i found the part one for this tutorial
many thanks for you
wait your response
thanks
Regards;
hello
this is great tutorial about se_linux
but i want to know where can i found the part one for this tutorial
many thanks for you
wait your response
thanks
Regards;
hello
this is great tutorial about se_linux
but i want to know where can i found the part one for this tutorial
many thanks for you
wait your response
thanks
Regards;
Hi,
Useful Article….
Where Can I find the Part 1 of this article…
Many Thanks Varad Gupta….
good article. I wish I could read all parts of your series (I found 2 and 5), what about 1,3,4 and any others.
How do I setup the domain of a service started by init.d? A process of this service needs access to all of /proc, but with the inherited domain init_t, it cannot access aall it needs to.