SELinux: Basic Configuration and Modes
Introduction
Security-Enhanced Linux (SELinux) is a mandatory access control (MAC) security mechanism built into the Linux kernel that provides an additional layer of system security beyond traditional discretionary access control (DAC). Originally developed by the National Security Agency (NSA), SELinux has become a critical component of enterprise Linux distributions, particularly Red Hat Enterprise Linux, CentOS, and Fedora.
SELinux enforces security policies that define how processes, users, and files interact with each other and system resources. By implementing the principle of least privilege at the kernel level, SELinux significantly reduces the potential damage from security vulnerabilities, misconfigurations, and compromised applications.
This comprehensive guide explores SELinux fundamentals, configuration options, operational modes, and best practices. Whether you're a system administrator new to SELinux or looking to deepen your understanding of this powerful security framework, this guide provides the knowledge and practical techniques needed to effectively implement and manage SELinux in production environments.
Understanding SELinux and Security Context
What Is SELinux?
Security-Enhanced Linux (SELinux) is a Linux kernel security module that provides a mechanism for supporting mandatory access control (MAC) security policies. Unlike traditional Unix permissions that rely on user discretion, SELinux enforces system-wide security policies that cannot be overridden by users or applications.
How SELinux Works
SELinux operates using several key concepts:
1. Security Contexts (Labels)
Every file, process, port, and system object has a security context with four components:
user:role:type:level
- User: SELinux user (different from Linux user)
- Role: Defines which SELinux users can access the object
- Type: Primary mechanism for access control (type enforcement)
- Level: Multi-Level Security (MLS) and Multi-Category Security (MCS)
Example: system_u:object_r:httpd_sys_content_t:s0
2. Type Enforcement
The most important SELinux feature, type enforcement uses types (domains for processes, types for files) to determine access:
- Processes run in specific domains (e.g.,
httpd_tfor Apache) - Files are labeled with specific types (e.g.,
httpd_sys_content_tfor web content) - Policy rules define which domains can access which types
3. Policy Rules
SELinux policies contain rules that explicitly allow or deny access:
allow httpd_t httpd_sys_content_t:file { read getattr open };
This rule allows the Apache process (httpd_t domain) to read files labeled as httpd_sys_content_t.
SELinux Operational Modes
SELinux operates in three distinct modes:
Enforcing Mode
- SELinux policies are enforced
- Access violations are denied and logged
- Provides active protection
- Recommended for production systems
Permissive Mode
- SELinux policies are not enforced
- Access violations are logged but allowed
- Useful for troubleshooting and policy development
- No actual security protection
Disabled Mode
- SELinux is completely disabled
- No policies loaded or enforced
- No logging of violations
- Not recommended for production systems
Why SELinux Matters
SELinux provides critical security benefits:
- Containment: Limits damage from compromised applications
- Mandatory access control: Cannot be circumvented by users or applications
- Zero-day protection: Reduces exploit effectiveness even before patches available
- Compliance: Required for many security frameworks and government certifications
- Fine-grained control: Precise control over system resource access
- Defense in depth: Additional security layer beyond traditional permissions
Common SELinux Misconceptions
Myth: "SELinux is too complex and should be disabled" Reality: Modern tools simplify SELinux management, and disabling removes critical security protections
Myth: "SELinux breaks applications" Reality: Properly labeled applications work seamlessly; issues indicate configuration problems
Myth: "SELinux is only for government/military" Reality: Any organization handling sensitive data benefits from SELinux
Prerequisites
Before configuring SELinux, ensure you have:
System Requirements
- Operating System: RHEL, CentOS, Fedora, or other SELinux-capable distribution
- Kernel: Linux kernel 2.6 or later with SELinux support
- Root Access: Administrative privileges required
- Disk Space: Adequate space for policy files and logs
Required Knowledge
- Basic Linux system administration
- Understanding of file permissions and ownership
- Command-line proficiency
- Basic understanding of system services
- Familiarity with log analysis
Software Requirements
Most SELinux tools come pre-installed on RHEL/CentOS systems:
- selinux-policy: SELinux reference policy
- policycoreutils: SELinux core utilities
- policycoreutils-python-utils: Python utilities for SELinux
- setroubleshoot-server: SELinux troubleshooting tools
- setools-console: SELinux policy analysis tools
Verification and Installation
Check if SELinux is installed:
rpm -qa | grep selinux
Install missing tools (CentOS/RHEL 8+):
sudo dnf install policycoreutils policycoreutils-python-utils setroubleshoot-server setools-console
For CentOS/RHEL 7:
sudo yum install policycoreutils policycoreutils-python setroubleshoot-server setools-console
Verify SELinux kernel support:
cat /sys/fs/selinux/enforce
If the file exists, SELinux is supported.
Step-by-Step SELinux Configuration
Step 1: Check Current SELinux Status
View detailed SELinux status:
sestatus
Expected output:
SELinux status: enabled
SELinuxfs mount: /sys/fs/selinux
SELinux root directory: /etc/selinux
Loaded policy name: targeted
Current mode: enforcing
Mode from config file: enforcing
Policy MLS status: enabled
Policy deny_unknown status: allowed
Memory protection checking: actual (secure)
Max kernel policy version: 33
Quick status check:
getenforce
Returns: Enforcing, Permissive, or Disabled
View current security context:
id -Z
Example output: unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c1023
Step 2: Understand SELinux Configuration Files
Main configuration file:
cat /etc/selinux/config
Content:
# This file controls the state of SELinux on the system.
# SELINUX= can take one of these three values:
# enforcing - SELinux security policy is enforced.
# permissive - SELinux prints warnings instead of enforcing.
# disabled - No SELinux policy is loaded.
SELINUX=enforcing
# SELINUXTYPE= can take one of these values:
# targeted - Targeted processes are protected,
# minimum - Modification of targeted policy. Only selected processes are protected.
# mls - Multi Level Security protection.
SELINUXTYPE=targeted
Policy types explained:
- targeted: Default policy, protects network-facing services
- minimum: Minimal protection, only critical services
- mls: Multi-Level Security for classified environments
Step 3: Change SELinux Modes
Temporarily change to permissive mode (until reboot):
sudo setenforce 0
Temporarily change to enforcing mode:
sudo setenforce 1
Verify the change:
getenforce
Permanently change SELinux mode:
Edit /etc/selinux/config:
sudo nano /etc/selinux/config
Change the SELINUX line:
SELINUX=enforcing # or permissive or disabled
Reboot for permanent changes to take effect:
sudo reboot
WARNING: Changing from disabled to enabled requires relabeling the entire filesystem on next boot.
Step 4: Enable SELinux from Disabled State
If SELinux is currently disabled:
-
Edit configuration:
sudo nano /etc/selinux/configChange to:
SELINUX=permissive SELINUXTYPE=targeted -
Reboot the system:
sudo reboot -
After reboot, system will relabel all files (may take time)
-
Verify permissive mode is working:
sestatus -
Check logs for issues:
sudo grep "SELinux" /var/log/messages -
If no critical issues, switch to enforcing:
sudo nano /etc/selinux/configChange to:
SELINUX=enforcing -
Reboot again:
sudo reboot
Step 5: Manage SELinux Contexts
View file security contexts:
ls -Z /var/www/html/
Example output:
-rw-r--r--. root root unconfined_u:object_r:httpd_sys_content_t:s0 index.html
View process contexts:
ps auxZ | grep httpd
View port contexts:
sudo semanage port -l | grep http
Change file context temporarily:
sudo chcon -t httpd_sys_content_t /var/www/html/newfile.html
Change file context permanently:
sudo semanage fcontext -a -t httpd_sys_content_t "/var/www/html/newfile.html"
sudo restorecon -v /var/www/html/newfile.html
Restore default contexts:
sudo restorecon -Rv /var/www/html/
Options:
-R: Recursive-v: Verbose-F: Force reset
Step 6: Manage SELinux Booleans
SELinux booleans allow runtime modification of policy behavior without rewriting policies.
List all booleans:
getsebool -a
Search for specific boolean:
getsebool -a | grep httpd
Check specific boolean:
getsebool httpd_can_network_connect
Enable boolean temporarily (until reboot):
sudo setsebool httpd_can_network_connect on
Enable boolean permanently:
sudo setsebool -P httpd_can_network_connect on
Common useful booleans:
# Allow httpd to connect to network
sudo setsebool -P httpd_can_network_connect on
# Allow httpd to connect to databases
sudo setsebool -P httpd_can_network_connect_db on
# Allow httpd to send mail
sudo setsebool -P httpd_can_sendmail on
# Allow FTP full access
sudo setsebool -P ftpd_full_access on
# Allow Samba to share home directories
sudo setsebool -P samba_enable_home_dirs on
Step 7: Manage SELinux Port Labeling
View port labels:
sudo semanage port -l
Add custom port for service (e.g., Apache on port 8080):
sudo semanage port -a -t http_port_t -p tcp 8080
Modify existing port label:
sudo semanage port -m -t http_port_t -p tcp 8080
Delete port label:
sudo semanage port -d -t http_port_t -p tcp 8080
View custom modifications:
sudo semanage port -l -C
Step 8: Create Custom SELinux Policies
For recurring denials, create custom policies:
-
Identify the denial in logs:
sudo ausearch -m avc -ts recent -
Generate policy module:
sudo grep denied /var/log/audit/audit.log | audit2allow -M mypolicy -
Review the generated policy:
cat mypolicy.te -
Install the policy module:
sudo semodule -i mypolicy.pp -
Verify installation:
sudo semodule -l | grep mypolicy
Remove custom module:
sudo semodule -r mypolicy
Advanced SELinux Hardening Tips
1. Use Confined Users
Create confined Linux user:
sudo useradd -Z user_u username
Map Linux user to SELinux user:
sudo semanage login -a -s user_u username
View user mappings:
sudo semanage login -l
Confine administrative users:
sudo semanage login -a -s staff_u adminuser
2. Implement Multi-Category Security (MCS)
Label files with categories:
sudo chcon -l s0:c0,c1 /path/to/file
Run process with specific category:
runcon -l s0:c0,c1 command
3. Audit SELinux Policy
Search for type enforcement rules:
sesearch -A -s httpd_t -t httpd_sys_content_t
Find which processes can access a type:
sesearch -A -t httpd_sys_content_t
Check for specific permission:
sesearch -A -s httpd_t -c file -p write
4. Implement File Context Equivalency
Make one directory context equivalent to another:
sudo semanage fcontext -a -e /var/www/html /srv/website
sudo restorecon -Rv /srv/website
5. Monitor SELinux Denials in Real-Time
Watch audit log:
sudo tail -f /var/log/audit/audit.log | grep denied
Use sealert for human-readable alerts:
sudo sealert -a /var/log/audit/audit.log
Set up automatic email alerts:
Install and configure setroubleshoot-server, which automatically sends alerts.
6. Optimize SELinux Performance
Disable unnecessary booleans:
Review and disable booleans not needed for your environment.
Use targeted policy:
Avoid MLS policy unless specifically required.
Minimize custom policies:
Use built-in policy features when possible.
7. Implement Confined Services
Ensure critical services run confined:
ps -eZ | grep -E '(httpd|nginx|mysqld|postfix)'
Verify they show specific domain (e.g., httpd_t), not unconfined_t.
8. Regular Policy Updates
Keep SELinux policies current:
sudo dnf update selinux-policy\*
Verification and Testing
Verify SELinux is Enforcing
Check status:
getenforce
sestatus
Verify policy is loaded:
sudo semodule -l
Test File Context Application
Create test file:
sudo touch /var/www/html/test.html
Check automatic labeling:
ls -Z /var/www/html/test.html
Should show httpd_sys_content_t
Test context restoration:
sudo chcon -t user_home_t /var/www/html/test.html
ls -Z /var/www/html/test.html
sudo restorecon -v /var/www/html/test.html
ls -Z /var/www/html/test.html
Test SELinux Denials
Attempt unauthorized action:
sudo -u apache touch /root/test
Check for denial:
sudo ausearch -m avc -ts recent
Verify Boolean Changes
Change boolean and verify:
getsebool httpd_can_network_connect
sudo setsebool httpd_can_network_connect on
getsebool httpd_can_network_connect
Monitor System Behavior
Check for unexpected denials:
sudo ausearch -m avc -ts today
Use setroubleshoot:
sudo sealert -a /var/log/audit/audit.log
Troubleshooting Common Issues
Issue 1: Service Won't Start After Enabling SELinux
Symptoms: Service fails to start with permission errors
Solutions:
-
Check for denials:
sudo ausearch -m avc -ts recent | grep service_name -
Use sealert for suggestions:
sudo sealert -a /var/log/audit/audit.log -
Verify file contexts:
ls -Z /path/to/service/files sudo restorecon -Rv /path/to/service/files -
Check for required booleans:
getsebool -a | grep service_name
Issue 2: Web Server Can't Access Files
Symptoms: Apache/Nginx returns 403 errors
Solutions:
-
Check file contexts:
ls -Z /var/www/html/ -
Apply correct context:
sudo semanage fcontext -a -t httpd_sys_content_t "/var/www/html(/.*)?" sudo restorecon -Rv /var/www/html/ -
For user directories:
sudo setsebool -P httpd_enable_homedirs on
Issue 3: Custom Port Not Working
Symptoms: Service can't bind to non-standard port
Solutions:
-
Check current port labels:
sudo semanage port -l | grep http -
Add custom port:
sudo semanage port -a -t http_port_t -p tcp 8080 -
Verify addition:
sudo semanage port -l | grep 8080
Issue 4: System Won't Boot After Enabling SELinux
Symptoms: System hangs or fails to boot
Solutions:
-
Boot into permissive mode:
- Edit GRUB boot parameters
- Add:
enforcing=0
-
After boot, check for issues:
sudo ausearch -m avc -ts today -
Fix issues, then re-enable:
sudo setenforce 1
Issue 5: Relabeling Takes Too Long
Symptoms: Filesystem relabeling during boot is very slow
Solutions:
-
Create autorelabel flag:
sudo touch /.autorelabel sudo reboot -
Or relabel while running:
sudo fixfiles -F onboot sudo reboot -
For specific paths only:
sudo restorecon -Rv /specific/path
Issue 6: Unknown Denials
Symptoms: Denials without clear cause
Solutions:
-
Use audit2why:
sudo ausearch -m avc -ts recent | audit2why -
Get detailed explanation:
sudo sealert -l <alert_id> -
Check dontaudit rules:
sudo semodule -DB # Temporarily disable dontaudit # Reproduce issue sudo semodule -B # Re-enable dontaudit
Best Practices for SELinux Management
1. Deployment Strategy
- Never disable SELinux: Use permissive mode for troubleshooting instead
- Start with permissive: New deployments should begin in permissive mode
- Gradual enforcement: Move to enforcing after resolving all denials
- Test thoroughly: Test in non-production before enforcing in production
- Plan relabeling: Schedule filesystem relabeling during maintenance windows
2. Operational Practices
- Monitor regularly: Set up automated monitoring of SELinux denials
- Use standard paths: Adhere to FHS to leverage default contexts
- Leverage booleans: Use booleans before creating custom policies
- Minimal custom policies: Rely on default policy when possible
- Document changes: Maintain records of all SELinux customizations
3. Troubleshooting Workflow
- Identify the denial in audit logs
- Use sealert/audit2why for analysis
- Check for existing booleans that solve the issue
- Verify file contexts are correct
- Only create custom policy as last resort
- Test solutions in permissive mode first
4. Security Hardening
- Enforce on all systems: Run production systems in enforcing mode
- Confine users: Use confined users for interactive accounts
- Audit custom policies: Regularly review custom policy modules
- Minimize permissions: Apply principle of least privilege
- Keep updated: Regularly update SELinux policies
5. Policy Management
- Use policy modules: Create separate modules for different customizations
- Version control: Track custom policies in version control
- Policy documentation: Document why custom policies were created
- Review regularly: Audit custom policies quarterly
- Remove unused: Delete obsolete custom policy modules
6. Compliance and Auditing
- Enable auditing: Ensure audit daemon is running
- Log retention: Maintain SELinux logs per compliance requirements
- Regular reviews: Monthly review of SELinux denials and customizations
- Security assessments: Include SELinux configuration in security audits
- Policy compliance: Verify policy meets organizational security standards
7. Training and Documentation
- Team training: Ensure administrators understand SELinux fundamentals
- Runbooks: Maintain documentation for common SELinux tasks
- Incident procedures: Document response procedures for SELinux issues
- Knowledge sharing: Share solutions to unique SELinux challenges
- Stay current: Follow SELinux project updates and best practices
Conclusion
SELinux provides robust mandatory access control that significantly enhances Linux system security. While often perceived as complex, SELinux becomes manageable and valuable once you understand its fundamental concepts and operational modes. This comprehensive guide has covered everything from basic configuration to advanced policy management, providing you with the knowledge to effectively implement and maintain SELinux in production environments.
Key takeaways:
- Essential security layer: SELinux provides critical protection beyond traditional permissions
- Three operational modes: Enforcing, permissive, and disabled each serve specific purposes
- Context-based security: Understanding security contexts is fundamental to SELinux
- Gradual implementation: Start with permissive mode, resolve issues, then enforce
- Built-in solutions: Leverage booleans and default policies before creating custom rules
- Continuous monitoring: Regular monitoring and maintenance ensure optimal security
By following the practices outlined in this guide, you implement a powerful security mechanism that protects against both known and zero-day threats. SELinux is particularly effective at containing compromised applications, preventing privilege escalation, and protecting sensitive data through fine-grained access controls.
Remember that SELinux is not a replacement for other security measures but a complementary layer in a comprehensive defense-in-depth strategy. Combined with proper system hardening, network security, and security monitoring, SELinux significantly strengthens your overall security posture. Invest time in understanding and properly configuring SELinux—the security benefits far outweigh the initial learning curve, and modern troubleshooting tools make SELinux management increasingly accessible to administrators at all skill levels.


