Process rights management enables processes to be restricted at the command, user, role, or system level. The Solaris OS implements process rights management through privileges. Privileges decrease the security risk that is associated with one user or one process having full superuser capabilities on a system. Privileges and RBAC provide a compelling alternative model to the traditional superuser model.
Privileges Protect Kernel Processes
A privilege is a discrete right that a process requires to perform an operation. The right is enforced in the kernel. A program that operates within the bounds of the Solaris basic set of privileges operates within the bounds of the system security policy. setuid programs are examples of programs that operate outside the bounds of the system security policy. By using privileges, programs eliminate the need for calls to setuid.
Privileges discretely enumerate the kinds of operations that are possible on a system. Programs can be run with the exact privileges that enable the program to succeed. For example, a program that sets the date and writes the date to an administrative file might require the file_dac_write and sys_time privileges. This capability eliminates the need to run any program as root.
Historically, systems have not followed the privilege model. Rather, systems used the superuser model. In the superuser model, processes run as root or as a user. User processes were limited to acting on the user's directories and files. root processes could create directories and files anywhere on the system. A process that required creation of a directory outside the user's directory would run with a UID=0, that is, as root. Security policy relied on DAC, discretionary access control, to protect system files. Device nodes were protected by DAC. For example, devices owned by group sys could be opened only by members of group sys.
However, setuid programs, file permissions, and administrative accounts are vulnerable to misuse. The actions that a setuid process is permitted are more numerous than the process requires to complete its operation. A setuid program can be compromised by an intruder who then runs as the all-powerful root user. Similarly, any user with access to the root password can compromise the entire system.
In contrast, a system that enforces policy with privileges allows a gradation between user capabilities and root capabilities. A user can be granted privileges to perform activities that are beyond the capabilities of ordinary users, and root can be limited to fewer privileges than root currently possesses. With RBAC, a command that runs with privileges can be isolated in a rights profile and assigned to one user or role. Table 8-1 summarizes the gradation between user capabilities and root capabilities that the RBAC plus privileges model provides.
The privilege model provides greater security than the superuser model. Privileges that have been removed from a process cannot be exploited. Process privileges prevent a program or administrative account from gaining access to all capabilities. Process privileges can provide an additional safeguard for sensitive files, where DAC protections alone can be exploited to gain access.
Privileges, then, can restrict programs and processes to just the capabilities that the program requires. This capability is called the principle of least privilege. On a system that implements least privilege, an intruder who captures a process has access to only those privileges that the process has. The rest of the system cannot be compromised.
Some privileges have a limited effect on the system, and some have a broad effect. The definition of the proc_taskid privilege indicates its limited effect:
proc_taskid Allows a process to assign a new task ID to the calling process.
The definition of the file_setid privilege indicates its broad effect:
net_rawaccess Allow a process to have direct access to the network layer.
The privileges(5) man page provides descriptions of every privilege. The command ppriv -lv prints a description of every privilege to standard out.
Administrative Differences on a System With Privileges
Table 8-2 Visible Differences Between a System With Privileges and a System Without Privileges
Privileges and System Resources
In the Solaris Express Community Edition, the project.max-locked-memory and zone.max-locked-memory resource controls can be used to limit the memory consumption of processes that are assigned the PRIV_PROC_LOCK_MEMORY privilege. This privilege allows a process to lock pages in physical memory.
If you assign the PRIV_PROC_LOCK_MEMORY privilege to a rights profile, you can give the processes that have this privilege the ability to lock all memory. As a safeguard, set a resource control to prevent the user of the privilege from locking all memory. For privileged processes that run in a non-global zone, set the zone.max-locked-memory resource control. For privileged processes that run on a system, create a project and set the project.max-locked-memory resource control. For information about these resource controls, see Chapter 6, Resource Controls (Overview), in System Administration Guide: Virtualization Using the Solaris Operating System and Chapter 17, Non-Global Zone Configuration (Overview), in System Administration Guide: Virtualization Using the Solaris Operating System.
How Privileges Are Implemented
Every process has four sets of privileges that determine whether a process can use a particular privilege. The kernel automatically calculates the effective set of privileges. You can modify the initial inheritable set of privileges. A program that is coded to use privileges can reduce the program's permitted set of privileges. You can shrink the limit set of privileges.
The kernel recognizes a basic privilege set. On an unmodified system, each user's initial inheritable set equals the basic set at login. You can modify the user's initial inheritable set. You cannot modify the basic set.
E (Effective): basic I (Inheritable): basic P (Permitted): basic L (Limit): all
Therefore, at login, all users have the basic set in their inheritable set, their permitted set, and their effective set. A user's limit set contains all privileges. To put more privileges in the user's effective set, you must assign a rights profile to the user. The rights profile would include commands to which you have added privileges. You can also assign privileges directly to the user or role, though such privilege assignment can be risky. For a discussion of the risks, see Security Considerations When Directly Assigning Security Attributes.
How Processes Get Privileges
Processes can inherit privileges. Or, processes can be assigned privileges. A process inherits privileges from its parent process. At login, the user's initial inheritable set of privileges determines what privileges are available to the user's processes. All child processes of the user's initial login inherit that set.
You can also directly assign privileges to programs, users, and roles. When a program requires privileges, you assign the privileges to the program's executable in a rights profile. Users or roles that are permitted to run the program are assigned the profile that includes the program. At login or when a profile shell is entered, the program runs with privilege when the program's executable is typed in the profile shell. For example, a role that includes the Object Access Management profile is able to run the chmod command with the file_chown privilege.
When a role or user runs a program that has been directly assigned an additional privilege, the assigned privilege is added to the role or user's inheritable set. Child processes of the program that was assigned privileges inherit the privileges of the parent. If the child process requires more privileges than the parent process, the child process must be directly assigned those privileges.
Programs that are coded to use privileges are called privilege-aware programs. A privilege-aware program turns on the use of privilege and turns off the use of privilege during program execution. To succeed in a production environment, the program must be assigned the privileges that the program turns on and off.
For examples of privilege-aware code, see Chapter 2, Developing Privileged Applications, in Solaris Security for Developers Guide. To assign privileges to a program that requires privileges, see How to Add Privileges to a Command.
You, in your capacity as system administrator, are responsible for assigning privileges. Typically, you assign the privilege to a command in a rights profile. The rights profile is then assigned to a role or to a user. The Solaris Management Console provides the graphical user interface (GUI) to assign privileges. Privileges can also be assigned by using commands such as smuser and smrole. For more information on how to use the GUI to assign privileges, see Chapter 9, Using Role-Based Access Control (Tasks).
Privileges can also be assigned directly to a user. If you trust a subset of users to use a privilege responsibly throughout their sessions, you can assign the privilege directly. Good candidates for direct assignment are privileges that have a limited effect, such as proc_clock_highres. Poor candidates for direct assignment are privileges that have far-reaching effects, such as file_dac_write.
Privileges can also be denied to a user or to a system. Care must be taken when removing privileges from the initial inheritable set or the limit set of a user or a system.
Expanding a User or Role's Privileges
Users and roles have an inheritable set of privileges, and a limit set of privileges. The limit set cannot be expanded, since the limit set is initially all privileges. The initial inheritable set can be expanded for users, roles, and systems. A privilege that is not in the inheritable set can also be assigned to a process.
The assignment of privileges per process is the most precise way to add privileges. You can expand the number of privileged operations that a user can perform by enabling the user to assume a role. The role would be assigned profiles that include commands with added privileges. When the user assumes the role, the user gets the role's profile shell. By typing in the role's shell, the commands in the role's profiles execute with the added privileges.
You can also assign a profile to the user rather than to a role that the user assumes. The profile would include commands with added privileges. When the user opens a profile shell, such as pfksh, the user can execute the commands in the user's profile with privilege. In a regular shell, the commands do not execute with privilege. The privileged process can only execute in a privileged shell.
To expand the initial inheritable set of privileges for users, roles, or systems is a riskier way to assign privileges. All privileges in the inheritable set are in the permitted and effective sets. All commands that the user or role types in a shell can use the directly assigned privileges. Directly assigned privileges enable a user or role to easily perform operations that can be outside the bounds of their administrative responsiblities.
When you add to the initial inheritable set of privileges on a system, all users who log on to the system have a larger set of basic privileges. Such direct assignment enables all users of the system to easily perform operations that are probably outside the bounds of ordinary users.
Restricting a User or Role's Privileges
By removing privileges, you can prevent users and roles from performing particular tasks. You can remove privileges from the initial inheritable set, and from the limit set. You should carefully test removal of privileges before you distribute an initial inheritable set or a limit set that is smaller than the default set. By removing privileges from the initial inheritable set, you might prevent users from logging in. When privileges are removed from the limit set, a legacy setuid program might fail because the program requires a privilege that was removed.
Assigning Privileges to a Script
Scripts are executables, like commands. Therefore, in a rights profile, you can add privileges to a script just as you can add privileges to a command. The script runs with the added privileges when a user or role who has been assigned the profile executes the script in a profile shell. If the script contains commands that require privileges, the commands with added privileges should also be in the profile.
Privilege-aware programs can restrict privileges per process. Your job with a privilege-aware program is to assign the executable just the privileges that the program needs. You then test the program to see that the program succeeds in performing its tasks. You also check that the program does not abuse its use of privileges.
Privileges and Devices
The privilege model uses privileges to protect system interfaces that are protected by file permissions alone in the superuser model. In a system with privileges, file permissions are too weak to protect the interfaces. A privilege such as proc_owner could override file permissions and then give full access to all of the system.
Therefore, ownership of the device directory is not sufficient to open a device. For example, members of the group sys are no longer automatically allowed to open the /dev/ip device. The file permissions on /dev/ip are 0666, but the net_rawaccess privilege is required to open the device.
Device policy is controlled by privileges. The getdevpolicy command displays the device policy for every device. The device configuration command, devfsadm, installs the device policy. The devfsadm command binds privilege sets with open for reading or writing of devices. For more information, see the getdevpolicy(1M) and devfsadm(1M) man pages.
Device policy allows you more flexibility in granting permission to open devices. You can require different privileges or more privileges than the default device policy. The privilege requirements can be modified for the device policy and for the driver proper. You can modify the privileges when installing, adding, or updating a device driver.
The add_drv and update_drv commands can modify device policy entries and driver-specific privileges. You must be running a process with the full set of privileges to change the device policy. For more information, see the add_drv(1M) and update_drv(1M) man pages.
Privileges and Debugging
The Solaris OS provides tools to debug privilege failure. The ppriv command and the truss command provide debugging output. For examples, see the ppriv(1) man page. For a procedure, see How to Determine Which Privileges a Program Requires.