Privileges (Overview)
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.
Privilege Descriptions
Privileges are logically grouped on the basis of the area of the privilege.
FILE privileges – Privileges that begin with the string file operate on file system objects. For example, the file_dac_write privilege overrides discretionary access control when writing to files.
IPC privileges – Privileges that begin with the string ipc override IPC object access controls. For example, the ipc_dac_read privilege enables a process to read remote shared memory that is protected by DAC.
NET privileges – Privileges that begin with the string net give access to specific network functionality. For example, the net_rawaccess privilege enables a device to connect to the network.
PROC privileges – Privileges that begin with the string proc allow processes to modify restricted properties of the process itself. PROC privileges include privileges that have a very limited effect. For example, the proc_clock_highres privilege enables a process to use high resolution timers.
SYS privileges – Privileges that begin with the string sys give processes unrestricted access to various system properties. For example, the sys_linkdir privilege enables a process to make and break hard links to directories.
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
A system that has privileges has several visible differences from a system that
does not have privileges. The following table lists some of the differences.
Table 8-2 Visible Differences Between a System With Privileges and a System Without Privileges
Feature |
No Privileges |
Privileges |
Daemons |
Daemons
run as root. |
Daemons run as the user daemon. For example, the following daemons
have been assigned appropriate privileges and run as daemon: lockd, mountd, nfsd, and
rpcbind. |
Log File Ownership |
Log files are owned by root. |
Log files are now owned
by daemon, who created the log file. The root user does not own
the file. |
Error Messages |
Error messages refer to superuser. For example, chroot: not superuser. |
Error messages reflect the
use of privileges. For example, the equivalent error message for chroot failure is chroot: exec failed. |
setuid
Programs |
Programs use setuid to complete tasks that ordinary users are not allowed to
perform. |
Many setuid programs have been changed to run with privileges. For example, the following
utilities use privileges: ufsdump, ufsrestore, rsh, rlogin, rcp, rdist, ping, traceroute, and
newtask. |
File Permissions |
Device permissions are controlled by DAC. For example, members of the group
sys can open /dev/ip. |
File permissions (DAC) do not predict who can open
a device. Devices are protected with DAC and device policy. For example, the /dev/ip
file has 666 permissions, but the device can only be opened by a
process with the appropriate privileges. Raw sockets are still protected by DAC. |
Audit Events |
Auditing
the use of the su command covers many administrative functions. |
Auditing the use of
privileges covers most administrative functions. The pm and as audit classes include audit events
that configure device policy and audit events that set privileges. |
Processes |
Processes are protected
by who owns the process. |
Processes are protected by privileges. Process privileges and
process flags are visible as a new entry in the /proc/<pid> directory, priv. |
Debugging |
No
reference to privileges in core dumps. |
The ELF note section of core dumps
includes information about process privileges and flags in the NT_PRPRIV and NT_PRPRIVINFO notes. The
ppriv utility and other utilities show the proper number of properly sized sets.
The utilities correctly map the bits in the bit sets to privilege names. |
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.
Effective privilege set, or E – Is the set of privileges that is currently in effect. A process can add privileges that are in the permitted set to the effective set. A process can also remove privileges from E.
Permitted privilege set, or P – Is the set of privileges that is available for use. Privileges can be available to a program from inheritance or through assignment. An execution profile is one way to assign privileges to a program. The setuid command assigns all privileges that root has to a program. Privileges can be removed from the permitted set, but privileges cannot be added to the set. Privileges that are removed from P are automatically removed from E.
A privilege-aware program removes the privileges that a program never uses from the program's permitted set. In this way, unnecessary privileges cannot be exploited by the program or a malicious process. For more information on privilege-aware programs, see Chapter 2, Developing Privileged Applications, in Solaris Security for Developers Guide.
Inheritable privilege set, or I – Is the set of privileges that a process can inherit across a call to exec. After the call to exec, the permitted and the effective sets are equal, except in the special case of a setuid program.
For a setuid program, after the call to exec, the inheritable set is first restricted by the limit set. Then, the set of privileges that were inherited (I), minus any privileges that were in the limit set (L), are assigned to P and E for that process.
Limit privilege set, or L – Is the outside limit of what privileges are available to a process and its children. By default, the limit set is all privileges. Processes can shrink the limit set but can never extend the limit set. L is used to restrict I. Consequently, L restricts P and E at the time of exec.
If a user has been assigned a profile that includes a program that has been assigned privileges, the user can usually run that program. On an unmodified system, the program's assigned privileges are within the user's limit set. The privileges that have been assigned to the program become part of the user's permitted set. To run the program that has been assigned privileges, the user must run the program from a profile shell.
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.
On an unmodified system, a user's privilege sets at login would appear similar
to the following:
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.
Assigning Privileges
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.