Chapter 3: Managing User Logins

When we log in to an SELinux-enabled system, we receive an SELinux context to work in. This context contains an SELinux user, an SELinux role, a domain, and optionally, a sensitivity range. As the SELinux user defines the roles and types that can be accessed, managing user logins and SELinux users is the first step in configuring end users on the system.

To enable properly configured users, we will learn to define users that have sufficient rights to do their jobs, ranging from regular users with strict SELinux protections to fully privileged administrative users with few SELinux protections. We will create and assign categories and sensitivities, as well as assign roles to users and use various tools to switch roles. At the end of the chapter, we will see how SELinux integrates with the Linux authentication process.

In this chapter, we're going to cover the following main topics:

  • User-oriented SELinux contexts
  • SELinux users and roles
  • Handling SELinux roles
  • SELinux and PAM

Technical requirements

Check out the following video to see the Code in Action: https://bit.ly/3jbASmr

User-oriented SELinux contexts

Once logged in to a system, our user will run inside a certain context. This user context defines the rights and privileges that we, as a user, have on the system. The command to obtain current user information, id, also supports displaying the current SELinux context information:

$ id -Z

unconfined_u:unconfined_r:unconfined_t:s0-s0:c0.c1023

On SELinux systems with a targeted policy type, chances are very high that all users are logged in as unconfined_u (the first part of the context). On more restricted systems, the user can be user_u (regular restricted users), staff_u (operators), sysadm_u (system administrators), or any of the other SELinux users.

The SELinux user defines the roles that the user can switch to. SELinux roles themselves define the application domains that the user can use. By default, a fixed number of SELinux users are available on the system, but administrators can create additional SELinux users. It is also the administrator's task to assign Linux logins to SELinux users.

SELinux roles, on the other hand, cannot be created through administrative commands, as SELinux roles are part of the SELinux policy. For this, the SELinux policy needs to be enhanced with additional rules that create the role. We will touch upon that in Chapter 15, Using the Reference Policy.

To view the currently available roles, use seinfo:

# seinfo --role

Roles: 14

  auditadm_r

  dbadm_r

  ...

  xguest_r

SELinux roles can be coarse-grained (such as sysadm_r) or more functionality-oriented (such as dbadm_r). Custom SELinux roles can even be very fine-grained, only granting the ability to transition into limited domains.

Let's see how to create and manage SELinux users.

SELinux users and roles

In SELinux-enabled environments, the login binary calls the libselinux API to establish the initial mapping between SELinux users and local users. Then, after finding the right SELinux user, the system looks up the role and domain that the user should be in and sets that as the user's context.

Listing SELinux user mappings

When logged in to the system, we can use id -Z to obtain the current SELinux context. For many users, this context will be defined by the unconfined user (unconfined_u), regardless of their username. If not that, it will generally be a context based on one of sysadm_u, staff_u, or user_u. This is because most Linux distributions will only provide a limited set of SELinux users by default, aligned with the SELinux roles that they support.

During login, the service process through which the login is handled will check a local definition file to find the appropriate mapping between the Linux account and the SELinux user. Let's look at the existing login mappings using semanage login -l. The following output is the default output on a CentOS system:

# semanage login -l

Login Name SELinux User MLS/MCS Range Service

__default__ unconfined_u s0-s0:c0.c1023 *

root unconfined_u s0-s0:c0.c1023 *

The output of the command shows one login mapping per line. Each mapping consists of the following:

  • The Login Name for which the mapping is applicable (that is, the username)
  • The SELinux User to which the login is mapped
  • The MLS/MCS Range to which the login is mapped
  • The Service for which the mapping applies (this is used for local customizations, which we will tackle in the Customizing logins for services section)

The login name can contain a few special values that do not map directly to a single Linux account:

  • __default__ is a catch-all rule. If none of the other rules match, then the users are mapped to the SELinux user identified through this line. In the given example, all users are mapped to the unconfined_u SELinux user, meaning regular Linux users are hardly confined in their actions. When this isn't meant to happen, administrators usually map regular logins to restricted SELinux users, while administrative logins are mapped to the staff_u or sysadm_u SELinux users.
  • Login names starting with % will map to groups. This allows administrators to map a group of people directly to an SELinux user rather than having to manage the mappings individually.

When both an individual user mapping and group mapping match, then the individual user mapping takes precedence. When multiple group definitions exist, then SELinux will use the first matching group mapping (in the order listed in the underlying seusers configuration file).

Important note

System processes (non-interactively logged-in Linux accounts) are mapped to the system_u SELinux user. This SELinux user should never be assigned to end user logins.

In the case of an MLS- or MCS-enabled system, the mapping contains information about the user's allowed sensitivity range (MLS/MCS range). This way, we can map multiple users to the same restricted SELinux user, while differentiating between these users through the allowed sensitivities. For instance, one user might only be allowed to access low-sensitivity areas (s0), whereas another user might also have access to higher sensitivities (for example, s1) or different categories.

Mapping logins to SELinux users

Let's use a few examples to show how we make these mappings work. For more intricate details on this, see the SELinux and PAM section. We'll assume we have a Linux user called lisa, and we want her account to be mapped to the staff_u SELinux user, whereas all other users in the users group are mapped to the user_u SELinux user.

We can accomplish this through the semanage login command, using the -a (add) option:

# semanage login -a -s staff_u lisa

# semanage login -a -s user_u %users

The -s parameter assigns the SELinux user to the given login, whereas the -r parameter handles the sensitivity (and categories) for that user. For instance, let's modify (using -m instead of -a) the recently created group-based definition by mapping to the staff_u user instead, and limiting these users to the s0-s0 sensitivity range and categories c0 to c4:

# semanage login -m -s staff_u -r "s0-s0:c0.c4" %users

The sensitivity range of a login mapping may not exceed the range assigned to the SELinux user. For example, if the staff_u SELinux user itself is only granted access to s0-s0:c0.c3, then the previous command will fail as it is trying to assign a broader access range. We'll discuss how to define SELinux users and their range in the Creating SELinux users section.

The semanage login command updates the seusers file located inside /etc/selinux/targeted. If multiple group mappings are defined, then the order of mappings within this file defines which mapping applies to a given user. Users that belong to multiple mapped groups will be assigned an SELinux user based on the first match.

While it is possible to update the order of the entries in the seusers file, this is not recommended. Every time semanage login modifies the seusers file, it will reorder the mappings. Instead, when a user belongs to multiple mapped groups, we advise you to create an individual (user-based) mapping. This is also shown whenever we create a group mapping for a group that contains users for which active mappings already exist:

# semanage login -a -s guest_u %nginx

libsemanage.add_user: User taylor is already mapped to group users, but also belongs to group nginx. Add an explicit mapping for this user to override group mappings.

The changes take effect when a new login occurs, so we should force a logout for these users. The following command kills all the processes of the lisa user, forcing a logout for that user:

# pkill -KILL -u lisa

Also, when we modify a user's settings, we should also reset the contexts of that user's home directory (while that user is not logged in). To accomplish this, use restorecon as follows:

# restorecon -RF /home/lisa

The -F option in the preceding command forces a reset, while -R does this recursively.

Important note

Running the restorecon -RF command will also reset file contexts that the user has manually set using tools such as chcon. We recommend defining SELinux user mappings up front, or recursively changing only the SELinux user of the files using chcon -R -u. The chcon application and file contexts are discussed in the next chapter.

To remove a login mapping, use the -d (delete) option. Don't forget to run the restorecon command afterward:

# semanage login -d lisa

# restorecon -RF /home/lisa

Don't forget to force a user logout again if this user is active on the system.

Customizing logins for services

When login mappings are added using semanage login, they apply to all services. There is no option in semanage to allow customizing the mappings based on the service. However, that does not mean it is not possible.

The SELinux user space tools and libraries will consult the following two configuration files to know what the mappings are:

  • The /etc/selinux/targeted/seusers file contains the standard, service-agnostic mappings. This file is managed by semanage login and should not be updated through any other means.
  • The /etc/selinux/targeted/logins directory contains customized mappings, one file per Linux account. So, the custom mapping for the root user will be in /etc/selinux/targeted/logins/root.

Inside the files for customized mappings, administrators can define, per service, a different SELinux user to map to. The services are the Pluggable Authentication Modules (PAM) services through which a user can log in, and more information on this can be found in the SELinux and PAM section.

For instance, to have the root user – when logged in through SSH – be mapped to the user_u SELinux user rather than their default unconfined_u user, the root file would need to contain the following:

sshd:user_u:s0

When querying the current mapping, semanage login will show this customization as follows:

# semanage login -l

...

Local customization in /etc/selinux/targeted/logins

root user_u s0 sshd

Of course, this customization does not need to be so drastic. It can also be used to limit the user's default MLS/MCS range. For instance, to limit the categories to c0.c8 (rather than the default c0.c1023 range) you would use the following:

sshd:unconfined_u:s0-s0:c0.c8

Such customizations allow us to flexibly change the access control policies based on the PAM service used.

Creating SELinux users

By default, only a small number of SELinux users are available for mapping to logins. If we want more control over the Linux accounts and their mappings, we need to create additional SELinux users.

First, list the currently known SELinux users using the semanage user -l command, as follows:

# semanage user -l

SELinux Labeling MLS/ MLS/

User Prefix MCS Level MCS Range SELinux Roles

guest_u user s0 s0 guest_r

root user s0 s0-s0:c0.c1023 staff_r ...

...

xguest_u user s0 s0 xguest_r

Next, create a new SELinux user with semanage user, using the -a (add) option. We need to give SELinux additional information about this SELinux user, such as the following:

  • The default sensitivity (using the -L option) for the SELinux user. This is the sensitivity that the user starts with.
  • The security clearance (using the -r option) applicable to the SELinux user. This range cannot be extended when defining login mappings. It is, however, possible to give a user a more limited range, as long as it is bounded by the current range.
  • The allowed role or roles (using the -R option) for the SELinux user.

    Tip

    The labeling prefix shown in the previous example is used to dynamically create SELinux policies with specific prefixes, such as <prefix>_home_t for user's home files. Most distributions leave this to the default user setting, and changing it is done through the (undocumented) -P parameter to semanage user.

In the following example, we're configuring the SELinux user finance_u:

# semanage user -a -L s0 -r "s0-s0:c0.c127" -R user_r finance_u

When the command creates the SELinux user, its information becomes part of the SELinux policy. From this point onward, administrators can map Linux accounts to this SELinux user.

Important note

SELinux roles are enabled through the SELinux user that a Linux account is mapped to. When an administrator wants to allow additional existing roles to a Linux account, the administrator either updates existing SELinux mappings to include the new role(s) or creates a new SELinux user that has access to the new role(s) and then maps this SELinux user to the Linux account.

Just like with login mappings, semanage user also accepts the -m option to modify an existing entry, or -d to delete one. For instance, the following command deletes the finance_u SELinux user:

# semanage user -d finance_u

Separate SELinux users enhance the audit information since SELinux users generally do not change during a user's session, whereas the effective Linux user ID can. If the user creates files or other resources, these resources also inherit the SELinux user part in their security context.

Listing accessible domains

When creating SELinux users, one of the parameters that needs to be provided is the role or roles for an SELinux user. Most of the roles are self-explanatory: the dbadm_r role is for DBAs, whereas the webadm_r role is for web application infrastructure administrators. If a role is not clear, or an administrator is not certain which accesses are part of a given role, the administrator can still query the SELinux policy for more information.

Informational note

This book will mostly focus on the command-line utilities used to query and interact with the active SELinux policy. In Chapter 13, Analyzing Policy Behavior, we will also cover the graphical utility apol.

As documented earlier, roles define which domains are accessible for the users associated with the role. We saw that seinfo can show us the available roles, but it can do more. It can list the domains accessible for a role as well, using the -x option:

# seinfo -r dbadm_r -x

Roles: 1

  role dbadm_r types { ... qmail_inject_t user_mail_t ... };

In this example, users running with the dbadm_r role as part of their security context will be able to transition to, for instance, the qmail_inject_t (the domain used to read email messages and pass those on to the qmail queue) and user_mail_t (the domain used for generic email-sending command-line applications) domains.

The information provided through the dominated roles is usually not of concern to the administrators. Role dominance, although supported in SELinux core, is not used by Linux distribution policies. It signifies the inheritance of (other) roles, but it will always just show the queried role.

Managing categories

Sensitivity labels and their associated categories are identified through numeric values, which is great for computers but not that obvious for users. Luckily, the SELinux utilities support translating the levels and categories to human-readable values, even though they are still stored as numbers. As a result, almost all tools that can show contexts will show them translated rather than presented as numerical values.

The translations are managed through the setrans.conf file, located in /etc/selinux/targeted. Inside this file, we can name specific values (for example, s0:c102) or ranges (such as s0-s0:c1.c127) with a string that is much easier for administrators to use. However, for translations to be performed, mcstransd – the MCS translation daemon – needs to be running.

Consider our example of the finance_u SELinux user who was allowed access to the c0.c127 category range. Two of the categories within that range are c102, which we will tag as Contracts, and c103, which we will tag as Salaries. The c1.c127 range will be labeled as FinanceData. The following diagram shows the relationship between these various categories:

Figure 3.1 – Relationship of the example categories and category range

Figure 3.1 – Relationship of the example categories and category range

To accomplish this, the following should be placed in the setrans.conf file:

s0:c102=Contracts

s0:c103=Salaries

s0-s0:c1.c127=FinanceData

After editing the setrans.conf file, the mcstransd application needs to be restarted.

These translations are handled by the SELinux utilities, which connect to the mcstransd daemon through the .setrans-unix socket located in /var/run/setrans to query the setrans.conf file. If the daemon is not running or the communication with the daemon fails, the numeric sensitivity and category values are displayed.

For instance, with the daemon running, the output of id -Z is now as follows:

# id -Z

unconfined_u:unconfined_r:unconfined_t:SystemLow-SystemHigh

We can view the available sensitivities and their human-readable counterparts using the chcat tool. The following example displays the translations after adding the finance-related ones:

$ chcat -L

s0 SystemLow

s0-s0:c0.c1023 SystemLow-SystemHigh

s0:c0.c1023 SystemHigh

s0:c102 Contracts

s0:c103 Salaries

s0-s0:c1.c127 FinanceData

The same chcat utility can be used to assign categories to users. For instance, to grant the Salaries category to the lisa Linux user, we'd use the following command:

# chcat -l -- +Salaries lisa

The previous command grants the Salaries category (c103) to the Linux user lisa. The user mapping is immediately updated with this information. Again, we need to make sure that the lisa user is logged out for the changes to take effect.

With this, we end our section on managing SELinux users and logins. We've learned how to align users with SELinux users so that they log in to the system with the correct context. In the next section, we will look at the SELinux roles and how to apply those to SELinux users.

Handling SELinux roles

We saw how SELinux users define the role(s) that a user can hold. But how does SELinux enforce which role a user logs in through? And when logged in, how can a user switch their active role?

Defining allowed SELinux contexts

To select the context assigned to a successfully authenticated user, SELinux introduces the notion of a default context. Based on the context of the service through which a user logs in (or through which the user executes commands), the system selects the right user context.

Inside the /etc/selinux/targeted/contexts directory, a file called default_contexts exists. Each line in this file starts with the SELinux context information of the parent process and is then followed by an ordered list of all the contexts that could be picked based on the user's allowed SELinux role(s).

Consider the following line of code for the sshd_t context:

system_r:sshd_t:s0 user_r:user_t:s0

                      staff_r:staff_t:s0

                      sysadm_r:sysadm_t:s0

                      unconfined_r:unconfined_t:s0

This line of code mentions that when a user logs in through a process running in the sshd_t domain, the listed roles are checked against the roles of the user. The user will transition to the first context listed that matches the roles the user can use.

For instance, assume we are mapped to an SELinux user that has access to both the staff_r and sysadm_r roles. In that case, we will log in as staff_r:staff_t since that is the first match.

However, like the seusers file for the Linux account mappings, the default_contexts file is a default file that can be overruled through specific customizations. These customizations are stored in the /etc/selinux/targeted/contexts/users subdirectory. These files are named after the SELinux user for which they take effect. This allows us to assign different contexts for particular SELinux users even if they share the same roles with other SELinux users. Because SELinux checks the entries per line, we do not need to copy the entire content of the default_contexts file. Only the configuration lines that we want to see a different configuration for need to be listed; SELinux will automatically use the default_contexts file for the rest.

Let's modify the default contexts so that the staff_u SELinux user logs in with the sysadm_r role (and with the sysadm_t type) when logged in through SSH. To do so, use the sshd_t line, modify it, and save the result as /etc/selinux/targeted/contexts/users/staff_u:

system_r:sshd_t:s0 sysadm_r:sysadm_t:s0

Specifically, for the SSH daemon, we also need to enable the ssh_sysadm_login boolean, which is a special precaution SELinux policy developers have made to prevent users from immediately logging in with highly privileged accounts:

# setsebool ssh_sysadm_login on

With these settings in place, we've set sysadm_r:sysadm_t:s0 as the only possible context, ensuring that the target context is staff_u:sysadm_r:sysadm_t.

Validating contexts with getseuser

To validate whether our change succeeded, we can ask SELinux what the result of a context choice will be without having to parse the files ourselves. We can accomplish this through the getseuser command, which takes two arguments: the Linux user account and the context of the process that switches the user context.

Important note

The getseuser command is a helper utility offered by the SELinux user space project, but is not made available on all distributions. You will find it on Debian and Gentoo, but not on CentOS or other Red Hat Enterprise Linux-derived distributions.

Here's an example that checks what the context would be for the sven user when they log in through a process running in the sshd_t domain:

# getseuser sven system_u:system_r:sshd_t

seuser: user_u, level s0-s0

Context 0 user_u:user_r:user_t:s0

One of the advantages of the getseuser command is that it asks the SELinux code what the context should be, which not only looks through the default_contexts and customized files, but also checks whether the target context can be reached or not, and that there are no other constraints that prohibit the change to this context.

Switching roles with newrole

After having successfully authenticated and logged in, users will be assigned the context through the configuration mentioned in the SELinux users and roles section. If the SELinux user has access to multiple roles, however, then the Linux user can use the newrole application to transition from one role to another.

Consider an SELinux system without unconfined domains and where we are, by default, logged in as the staff_r role. To perform administrative tasks, we need to switch to the sysadm_r administrative role, which we can do with the newrole command. This command only works when working through a secure terminal listed in /etc/securetty:

$ id -Z

staff_u:staff_r:staff_t:s0

$ newrole -r sysadm_r

Password: (Enter user password)

$ id -Z

staff_u:sysadm_r:sysadm_t:s0

Notice how the SELinux user remains constant but the role and domain have changed.

The newrole command can also be used to transition to a specific sensitivity, as follows:

$ newrole -l s0-s0:c0.c100

When we switch to another role or sensitivity, what we actually do is create a new session (with a new shell) that has this new role or sensitivity. The command does not change the context of the current session, nor does it exit from the current session.

We can return from our assigned role and go back to the first session by exiting (through exit, logout, or Ctrl + D).

Managing role access through sudo

Most administrators use sudo for privilege delegation: allowing users to run certain commands in a more privileged context than the user is otherwise allowed. The sudo application is also capable of switching SELinux roles and types.

We can pass the target role and type to sudo directly. For instance, we can tell sudo to switch to the administrative role when we edit a PostgreSQL configuration file:

$ sudo -r sysadm_r -t sysadm_t vim /var/lib/pgsql/data/pg_hba.conf

However, we can also configure sudo through the /etc/sudoers file to allow users to run commands within a certain role and/or type, or get a shell within a certain context. Consider a user that has access to both the user_r and dbadm_r roles (with the dbadm_r role being a role designated for database administrators). Within the sudoers file, the following line allows the myuser user to run any command through sudo, which, when triggered, will run with the dbadm_r role and within the dbadm_t domain:

myuser ALL=(ALL) TYPE=sysadm_t ROLE=sysadm_r ALL

Often, administrators will prefer sudo over newrole as the latter does not change the effective user ID, which is often required for end users when they want to invoke a more privileged command (concerning the root user or a service-specific runtime account) anyway. The sudo application also has great logging capabilities, and we can even have commands switching roles without requiring the end user to explicitly mention the target role and type. Sadly, it does not support changing sensitivities.

Reaching other domains using runcon

Another application that can switch roles and sensitivities is the runcon application. The runcon command is available for all users and is used to launch a specific command as a different role, type, and/or sensitivity. It even supports changing the SELinux user – assuming the SELinux policy lets you.

The runcon command does not have its own domain – it runs in the context of the user executing the command. As such, the privileges of the user domain itself govern the ability to change the role, type, sensitivity, or even SELinux user.

Most of the time, we will use runcon to launch applications with a particular category. This allows us to take advantage of the MCS approach in SELinux without requiring applications to be MCS-enabled:

$ runcon -l Salaries bash

$ id -Z

unconfined_u:unconfined_r:unconfined_t:Salaries

For instance, in the previous example, we run a shell session with the Salaries category (prohibiting it from accessing resources that do not have the same or fewer categories set).

Switching to the system role

Sometimes, administrators will need to invoke applications that should not run under their current SELinux user context but instead as the system_u SELinux user with the system_r SELinux role. SELinux policy administrators acknowledge this need, and allow a very limited set of domains to switch the SELinux user to a different user – perhaps contrary to the purpose of the immutability of SELinux users mentioned earlier. Yet, as there are cases where this is needed, SELinux needs to accommodate this. One of the applications allowed to switch the SELinux user is run_init (through its run_init_t domain).

The run_init application is mainly (almost exclusively) used to start background system services on a Linux system. Using this application, the daemons do not run under the user's SELinux context but the system's, as required by SELinux policies.

As this is only needed on systems where launching additional services is done through service scripts, distributions that use systemd do not require the use of run_init. systemd already runs with the system_r role and is responsible for starting additional services. As such, no role transition is needed. Other init systems, such as Gentoo's OpenRC, integrate run_init so that administrators do not generally need to invoke run_init manually.

Most SELinux policies enable role-managed support for selective service management (for non systemd distributions). This allows users that do not have complete system administration rights to still manipulate a select number of services on a Linux system, allowed by the SELinux policy. These users are to be granted the system_r role, but once accomplished, they do not need to call run_init to manipulate specific services anymore. The transitions happen automatically and only for the services assigned to the user – other services cannot be launched by these users.

This finalizes our section on handling SELinux roles. We've learned how to manage SELinux roles and switching roles and contexts, as well as how to define the target role and type in the case of privilege escalation. In the last section of this chapter, we will look at how PAM is used to configure the SELinux context setup on the system.

SELinux and PAM

With all the information about SELinux users and roles, we have not touched upon how exactly applications or services create and assign an SELinux context to a user. As mentioned earlier on, this is coordinated through the use of Linux's PAM services.

Assigning contexts through PAM

End users log in to a Linux system through either a login process (triggered through a getty process), a networked service (for example, the OpenSSH daemon), or through a graphical login manager (xdm, kdm, gdm, slim, and so on).

These services are responsible for switching our effective user ID (upon successful authentication, of course) so that we are not active on the system as the root user. For SELinux systems, these processes also need to switch the SELinux user (and role) accordingly, as otherwise, the context will be inherited from the service, which is obviously wrong for any interactive session.

In theory, all these applications can be made fully SELinux aware, linking with the SELinux user space libraries to get information about Linux mappings and SELinux users. Instead of converting all these applications, the developers decided to take the authentication route to the next level using the PAM services that Linux systems provide.

PAM offers a very flexible interface for handling different authentication methods on Linux (and Unix) systems. All applications mentioned earlier use PAM for their authentication steps. To enable SELinux support for these applications, we need to update their PAM configuration files to include the pam_selinux.so library.

The following code listing is an excerpt from CentOS's /etc/pam.d/remote file, limited to PAM's session service directives. It triggers the pam_selinux.so library code as part of the authentication process, as follows:

session required pam_selinux.so close

session required pam_loginuid.so

session required pam_selinux.so open

session required pam_namespace.so

session optional pam_keyinit.so force revoke

session include password-auth

session include postlogin

The arguments supported by the pam_selinux.so code are described in the pam_selinux manual page. In the preceding example, the close option clears the current context (if any), whereas the open option sets the context of the user. The pam_selinux module takes care of querying the SELinux configuration and finding the right mappings and context based on the service name used by the daemon.

Prohibiting access during permissive mode

Having SELinux active and enforcing on a system improves its resilience against successful exploits and other malicious activities, especially when the system is used as a shell server (or provides other interactive services) and the users are confined – meaning they are mapped to user_u or other confined SELinux users.

Some administrators might want to temporarily switch the system to permissive mode. This could be to troubleshoot issues or to support some changes made on the system. When using permissive mode, it would be a good idea to ensure that the interactive services are not usable for regular users.

With pam_sepermit, this can be enforced on the system. The PAM module will deny a set of defined users access to the system if the system is in permissive mode. By default, these users are mentioned in /etc/security/sepermit.conf, but a different file can be configured through the conf= option inside the PAM configuration itself.

In the sepermit.conf file, there are three approaches to document which users should be denied access when the system is in permissive mode:

  • Regular usernames
  • Group names, prefixed with the @ sign
  • SELinux usernames, prefixed with the % sign

Within this file, we list each user, group, or SELinux user on a single line. After each entry, we can (but don't have to) add one or two options:

  • exclusive means that the system will allow the user to be active even when the system is in permissive mode, but only a single session can be active. When the user logs out, all active processes will be killed.
  • ignore will return PAM_IGNORE as the return status if SELinux is in enforcing mode, and PAM_AUTH_ERR if SELinux is in permissive mode. This allows special constructs/branches for this user in PAM based on the permissive state of the system.

To enable pam_sepermit, it's sufficient to enable the module in the auth PAM service as follows:

auth required pam_sepermit.so

Of course, don't forget to remove all active user sessions when switching to permissive mode, as any running session is otherwise left untouched.

Polyinstantiating directories

The last PAM module we'll look at is pam_namespace.so. Before we dive into configuring this module, let's first look at what polyinstantiation is about.

Polyinstantiation is an approach where, when a user logs in to a system, the user gets a view on filesystem resources specific to its session, while optionally hiding the resources of other users. This differs from regular access controls, where the other resources are still visible, but might just be inaccessible.

This session-specific view, however, does not just use regular mounts. The module uses the Linux kernel namespace technology to force a (potentially more limited) view on the filesystem, isolated and specific to the user session. Other users have a different view on the filesystem.

Let's use a common example. Assume that all users, except root, should not have access to the temporary files generated by other users. With standard access controls, these resources would still be visible (perhaps not readable, but their existence or the directories they reside in would be visible). Instead, with polyinstantiation, a user will only see their own /tmp and /var/tmp views.

The following setting in /etc/security/namespace.conf will remap these two locations:

/tmp /tmp/tmp-inst/ level root

/var/tmp /var/tmp/tmp-inst/ level root

On the real filesystem, those locations will be remapped to a subdirectory inside /tmp/tmp-inst and /var/tmp/tmp-inst. The end users do not know or see the remapped locations – for them, /tmp and /var/tmp are as they would expect.

The format (and thus polyinstantiation) of the subdirectories created depends on the third option within the namespace.conf file. The supported options are as follows:

  • user, which will create a subdirectory named after the user (such as lisa)
  • level, which will create a subdirectory named after the user sensitivity level and username (such as system_u:object_r:tmp_t:s0-s0:c0.c1023_lisa)
  • context, which will create a subdirectory named after the process context (including the sensitivity level) and username (such as system_u:object_r:user_tmp_t:s0_lisa)

For SELinux systems, the most common setting is level.

Tip

In the default namespace.conf file, you might notice that this also has support for home directories. When enabled with the level or context method, this will ensure that users have a sensitivity-specific home directory set. For instance, if the system configuration forces the user to have a lower sensitivity when logged in through SSH than when the user logs in through the terminal, a different home directory view will be used.

In the previous example, only the root user is exempt from these namespace changes. Additional users can be listed (comma-separated), or an explicit list of users can be given for which polyinstantiation needs to be enabled (if we prefix the user list with the ~ character). To allow the namespace changes to take place, the target locations need to be available on the system with the 000 permission:

# mkdir /tmp-inst && chmod 000 /tmp-inst

Next, enable pam_namespace.so in the PAM configuration files at the session service:

session required pam_namespace.so

Finally, make sure that SELinux allows polyinstantiated directories. On CentOS, this is governed through the polyinstantiation_enabled SELinux boolean:

# setsebool polyinstantiation_enabled on

Other distributions will have it through the allow_polyinstantiation SELinux boolean.

With the polyinstantiation support, we close off this final section of the chapter, where we learned how PAM is used to trigger SELinux context changes on the system.

Summary

SELinux maps Linux users onto SELinux users and defines the roles a user can be assigned through the SELinux user definitions. We learned how to manage those mappings and SELinux users with the semanage application, and how to grant the right roles to the right people.

We also saw how the same commands are used to grant the proper sensitivity to the user and how we can describe these levels in the setrans.conf file. We used the chcat tool to do most of the category-related management activities.

After assigning roles to the users, we saw how to jump from one role to another using newrole, sudo, runcon, and run_init. We ended this chapter with important insights into how SELinux is integrated into the Linux authentication process and how to tune a Linux system further using a couple of SELinux-aware PAM modules.

In the next chapter, we will learn to manage the labels on files and processes, and see how we can query the SELinux policy rules.

Questions

  1. Why can't we just add an SELinux role to a Linux account?
  2. Can Linux accounts be mapped to more than one SELinux user?
  3. Besides associating the valid SELinux roles, what other advantages does an SELinux user have?
  4. What purpose does PAM have when dealing with Linux accounts and SELinux mappings?
..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
3.147.67.166