Most installations of Apache HTTP have some sort of dynamic content; in particular, CGI scripts are very common. This section examines a much more complicated use case for SELinux: A website that has a number of users, each of whom owns a virtual host, out of which they are allowed to run CGI content.
In this situation, we have a number of security goals:
Protect the system from the users
Protect the users from each other
Protect the user's home directory from their own CGI scripts
One common method for approaching the first two goals on a non-SELinux setup is to use an Apache HTTP module called suEXEC. You can read more about suEXEC at http://httpd.apache.org/docs-2.0/suexec.html. Using suEXEC protection, user CGI scripts run under their own uid. This ensures that user CGI scripts cannot interfere with the system Apache HTTP daemon (since it runs under its own uid), nor with each other (since each user has their own uid).
However, when CGI scripts are run via suEXEC using standard Linux security, a compromised, misconfigured, or simply buggy user CGI script has complete access to any other file the user owns, such as their home directory. It also has access to any process running under the same uid, and so forth. Given the security track record of Web software, protecting the user's personal data from CGI programs they may install is very desirable.
The SELinux policy specifies that when a user CGI script is executed by suEXEC, a domain transition occurs to change the script's security label to the httpd_sys_script_t type. This means the user's CGI scripts run in their own confined domain (but still the same uid). In the default Fedora Core setup, the httpd_sys_script_t domain can read and write to files and directories that have the httpd_sys_content_t type. But they still cannot access files with type user_home_t, in other words the user's home directory.
To illustrate this, here are example user names, file names, and websites involved. In this example, the virtual hosting provider has each user store their website in /var/www/sitename, and the content is all owned by the user. CGI scripts are allowed, and they can be installed anywhere in the user's site; the filename just has to end in .cgi. Here is an overview of the filesystem layout:
ls -Z /var/www/ drwxr-xr-x root root system_u:object_r:httpd_sys_content_t . drwxr-xr-x root root system_u:object_r:var_t .. drwxr-xr-x bob bob system_u:object_r:httpd_sys_content_t widgets.com drwxr-xr-x jane jane system_u:object_r:httpd_sys_content_t yoyodyne.org drwxr-xr-x sam sam system_u:object_r:httpd_sys_content_t sammy.net
Here is a sample of how the Apache HTTP configuration for the example.com domain might look. Note particularly that Apache HTTP has been configured to run CGI scripts as the user bob.
NameVirtualHost 10.23.54.2:80
<VirtualHost 10.23.54.2:80>
ServerAdmin webmaster@example.com
DocumentRoot /var/www/example.com/
ServerName web.example.com
ServerAlias example.com www.example.com
ErrorLog logs/example.com-error_log
CustomLog logs/example.com-access_log common
SuexecUserGroup bob bob
<Directory /var/www/example.com/>
Options +ExecCGI +Indexes
AddHandler cgi-script .cgi
</Directory>
</VirtualHost>
By using the normal Apache HTTP suEXEC mechanism, together with SELinux, you have achieved the major security goals set out at the beginning of this section. However, this is still only a fraction of SELinux's power.