Skip navigation

Glenn Faden's Blog

February 2018 Previous month Next month

In April 2014, I wrote a blog describing the use of authenticated rights profiles in Oracle Solaris 11.2. As the name implies, the rights assigned via authenticated profiles are only available after the user has been re-authenticated. In previous Solaris 11 releases the initial account that is created during system installation was granted access to sudo(8), the root role, and the System Administrator rights profile. In Oracle Solaris 11.4 the System Administrator assignment is specified using the auth_profiles keyword, so that re-authentication is required when using pfexec(1).  As is the case with sudo, a tty ticketing mechanism is used so that re-authentication is generally not required within a five-minute window.


While the choice of using sudo or pfexec may seem to be a matter of taste, the latter is optimized for Oracle Solaris, providing features like fine-grained auditing and fine-grained process attributes like extended policy privileges and process clearance. But I think the most interesting advantage is that commands in authenticated rights profiles are automatically recognized by the kernel without requiring sudo, pfexec, or special file permissions. Unlike sudo and su(8), which are set-uid-to-root binaries, pfexec is an unprivileged program. All of the available profiles shells (pfbash, pfsh, pfcsh, etc.) are simply hard links to pfexec. When your shell is pfbash you are be automatically challenged to re-authenticate when you execute any commands that have been assigned to you via authenticated profiles.


The architecture by which this is accomplished is based on two process flags, PRIV_PFEXEC and PRIV_PFEXEC_AUTH, and two helper programs, pfexecd and pfexec_auth. The steps are shown in the following two flow charts (click to enlarge):




Setting the PRIV_PFEXEC process flag is an unprivileged operation which is set by pfexec, and inherited by child processes. If this flag is set on a process being executed, the kernel makes a door up call to pfexecd, which invokes the name service to retrieve any process attributes that have been assigned to the user. If found, these attributes are returned to the kernel and applied to the process being executed.



However, if the command's RBAC attributes are found in an authenticated profile, and the process does not have the PRIV_PFEXEC_AUTH flag set, then the kernel executes the helper process pfexec_auth as root, in place of the original command, passing it the original user context. This helper process starts a PAM session using  the /etc/pam.d/pfexec stack. If the re-authentication is successful, pfexec_auth uses its privilege, proc_setid, to set the PRIV_PFEXEC_AUTH flag. If the user cancels the re-authentication challenge, then the PRIV_PFEXEC flag is cleared. In either case the original command is re-executed. If the the authentication is unsuccessful, then the original command is not executed.

The title of this blog may seem like an oxymoron since the obvious security policy would be to prohibit sharing labeled files. In fact, that is the default policy in Oracle Solaris 11.4 for NFS and SMB shares since the kernel-based implementations of NFS and SMB (a.k.a. CIFS) are label-aware.  Files and directories whose labels are higher than Admin_Low are not exposed to clients. The policy for sharing labeled file systems is described here.


An NFS administrator may override this restriction by setting the option labeled=on as described in share_nfs(8). There is currently no equivalent setting for the share_smb(8) option, so the remainder of the blog will focus on NFS. The following procedure can be used to enable labeled access to an NFS share.


     # zfs set share.nfs.labeled=on rpool/export/home

     # zfs set share.nfs=on rpool/export/home


When this option is enabled, access may be granted to files and directories whose labels are dominated by the user's clearance. The user's clearance is retrieved from the NFS server's name service after mapping the NFS client's identity to a local identity. This option requires that the NFS ID Mapper service, svc:/network/nfs/mapid, is enabled. The NFS server must either have local account clearances specified in user_attr(8) or must be an LDAP client of a server containing account clearances.  The kernel maintains a cache of mappings between users and clearances so that it can efficiently perform label dominance checks. To prevent spoofing the user's identity, the NFS share should also include strong authentication, such as the use of Kerberos:


          # zfs set rpool/export/home


Oracle Solaris 11.4 supports NFS Version 4.1, but that protocol has no mechanisms for clients to get or set file labels. Newly created files and directories on the NFS server simply inherit their labels from their parent directory. The NFS 4.2 protocol does support file labeling, and specifies various label interchange mechanisms for label transmission, including CIPSO and CALIPSO. Both of these mechanisms are present in the Oracle Solaris kernel because they are required for labeled networking when Trusted Extensions is enabled. But the Trusted Extensions model requires mutual trust between peers because the peer's label is applied to newly created objects. Each trusted system must identify the peers from which it is willing to receive labeled packets. This isn't practical or necessary for standard NFS servers.


In Oracle Solaris 11.4, file labels are inherited from their parent directory, not from the client. The API to set file labels, setflabel(3TSOL), is unprivileged, but the real user must have been assigned the authorizations solaris.label.file.upgrade and/or solaris.label.file.downgrade. So in a potential implementation of NFS 4.2 Labeled NFS for Oracle Solaris, these authorization checks could be added to the NFS map ID daemon, and the results could be included in the existing kernel clearance cache. Note that the NFS server would not need to be aware of the client's label encodings (the human readable format) because the label transmission and dominance checks operate on binary label structures.

The new clearance policy that I discussed in my blog about Protecting Sensitive Data is always enforced by the kernel, but is completely transparent by default, so there is no need for a switch for enabling or disabling this label-based policy. By default, all process are assigned the maximum clearance, Admin_High, and all files are assigned the minimum label, Admin_Low, so nothing is denied. Administrators can safely experiment with the new labeling interfaces while they refine their security policy. As they gain familiarity, they can make the policy increasingly robust by applying clearances to all users and SMF services, and by labeling filesystem objects. But it is important to remember that no process can raise its clearance nor observe any resource for which it is not cleared.


The default clearance for all user accounts and SMF services is specified via the CLEARANCE property in /etc/security/policy.conf. This property should eventually be set to Admin_Low, once explicit user clearances have been assigned administratively. SMF services that assign clearances to user processes, such as the RAD service, are explicitly assigned the Admin_High clearance. For example:


     # svccfg -s rad listprop method_context/clearance

     method_context/clearance astring    ADMIN_HIGH


Explicit clearances are specified in user_attr(5) and may be set by usermod(8), useradm(8), or the Account Manager BUI. A default clearance for newly created local or LDAP accounts can also be specified. For example:


     # useradd -S files -D -K clearance=Public

     # useradd -S ldap -K clearance=Public default@


As part of the policy, labels should be assigned to ZFS filesystem objects. Prior to setting labels, the multilevel property must be enabled on new or existing filesystems. For example, the following three steps will restrict access to the audit trail to processes with the Admin_High clearance.


     # zfs set multilevel=on rpool/VARSHARE

     # setlabel Admin_High /var/audit

     # audit -n


The following examples demonstrate how access to labeled data can be managed and monitored. First, to reduce the auditing overhead, the audit policy is adjusted to record all read access to labeled files, while ignoring read access to unlabeled files.


     # auditconfig -setpolicy +labeled_only

     # auditconfig -setflags fr,fw,fm,fd,ex,sstore

     user default audit flags = sstore,fr,fw,fm,fd,ex(0x28003902b,0x28003902b)


Using the compliance labels discussed in a previous blog, we lower root's current process clearance to the highest label in that encodings file so that root's audit records will include its clearance.


     # plabel "Confidential Highly Restricted" $$


Then we create two labeled filesystems whose access is only restricted by process clearance.


     # zfs create -o multilevel=on rpool/export/payments

     # setlabel "Confidential Payment Data" /export/payments


     # zfs create -o multilevel=on rpool/export/patients

     # setlabel "Confidential Health Records" /export/patients


     # chmod 777 /export/payments /export/patients


Next we create accounts for bob and alice as discussed previously:


     # useradm add -PK clearance="Confidential Payment Data" bob

     New Password->

     Confirm Password->

     Password Accepted


     # useradm add -PK clearance="Confidential Health Records" alice

     New Password->

     Confirm Password->

     Password Accepted


As bob, we create a file in /export/payments that is automatically labeled:


     bob$ touch /export/payments/foo

     bob$ getlabel !$

     /export/payments/foo: Confidential Payment Data


As alice, we create a file in /export/patients that is automatically labeled:


     alice$ touch /export/patients/bar

     alice$ getlabel !$

     /export/patients/bar: Confidential Health Records


Then alice tries to list the payments directory for which she is not cleared:


     alice$ ls /export/payments

     Permission denied


Finally, we can get a report of the entire sequence using a script which extracts the labeled records from the audit trail and reformats the results into an html file. This script must be executed with an Admin_High clearance since that is now the label of the audit trail.


     # plabel


     # /usr/demo/tsol/auditfiles.ksh auditlog.html


The tabular results are shown below. Note that only label-relevant events are shown, and that the process IDs for each event are hyperlinked to their corresponding commands. Reports like this are useful for accountability and compliance.



Oracle Solaris Audit Trail
Access Events Affecting Labeled Files
Date/TimePIDReal UserEffective UserEventPathnameData Label(s)Error Value
2018-02-07 16:34:37.371-08:0010378rootrootrelabel file/export/paymentsADMIN_LOW
Confidential Payment Data
2018-02-07 16:34:45.359-08:0010381rootrootrelabel file/export/patientsADMIN_LOW
Confidential Health Records
2018-02-07 16:34:55.219-08:0010382rootrootchmod(2)/export/paymentsConfidential Payment Data
2018-02-07 16:34:55.219-08:0010382rootrootchmod(2)/export/patientsConfidential Health Records
2018-02-07 16:37:25.426-08:0010461bobbobopen(2) - write,creat,trunc/export/payments/fooConfidential Payment Data
2018-02-07 16:38:36.930-08:0010489alicealiceopen(2) - write,creat,trunc/export/patients/barConfidential Health Records
2018-02-07 16:39:12.874-08:0010491alicealiceopen(2) - read/export/paymentsConfidential Payment Data
failure: Permission denied

Execution Events Affecting Labeled Files
Date/TimePIDAudit UserClearanceEventCommand# of FilesError Value
2018-02-07 16:34:37.369-08:0010378gfadenConfidential Highly Restrictedexecve(2)/usr/bin/setlabel Confidential Payment Data /export/payments  1success
2018-02-07 16:34:45.357-08:0010381gfadenConfidential Highly Restrictedexecve(2)/usr/bin/setlabel Confidential Health Records /export/patients  1success
2018-02-07 16:34:55.217-08:0010382gfadenConfidential Highly Restrictedexecve(2)/usr/bin/chmod 777 /export/payments /export/patients  2success
2018-02-07 16:37:25.424-08:0010461bobConfidential Payment Dataexecve(2)/usr/bin/touch /export/payments/foo  1success
2018-02-07 16:38:36.927-08:0010489aliceConfidential Health Recordsexecve(2)/usr/bin/touch /export/patients/bar  1success
2018-02-07 16:39:12.871-08:0010491aliceConfidential Health Recordsexecve(2)/usr/bin/ls /export/payments  1success

In April 2013 I posted a blog entry,  Getting Started with OpenLDAP, which included some shell scripts for configuring the OpenLDAP server to manage Oracle Solaris accounts. Back then the only supported tool for configuring an LDAP server was idsconfig(8), which only worked with Oracle Directory Server Enterprise Edition (ODSEE). The OpenLDAP server, slapd, is now fully supported in Solaris 11.4, and idsconfig has been replaced by a new tool, ldapservercfg(8).

The ldapservercfg tool is fully integrated with SMF and RBAC, and can be run interactively or automatically. It is well documented here so I won't repeat those instructions, but there are some interesting security aspects of the process that are worth noting. Unlike most administrative procedures, ldapservercfg and the SMF service svc:/network/ldap/server:openldap must be started by the openldap account, instead of root.

The RBAC profile OpenLDAP Server Administration specifies the required user, group, authorizations and privileges to properly execute ldapservercfg and to configure the slapd server. These RBAC attributes can be observed as follows:

gfaden@sol11:~$ profiles -lc ldapservercfg openldap


name=OpenLDAP Server Administration






gfaden@sol11:~$ auths list -u openldap



Administrators with this rights profile can run ldapservercfg interactively via a profile shell like pfexec or by su'ing to the openldap account, whose shell is pfbash. The tool reads its initial parameter values from the SMF service properties, and provides a menu driven interface to modify these values. When the server configuration is successful, the configuration properties are updated and the slapd server is started.

Alternatively, the SMF service can be enabled by an administrator using svcadm(8) or via an auto-install profile. Prior to enabling the service, the default service properties can be updated by svccfg(8).  If the slapd server has not been previously configured, ldapservercfg is run automatically by the service.

The ldapservercfg tool can optionally create the admin credentials required by the ShadowUpdate policy to support remote account administration. Two options are provided for password authentication. By default, the slapd server will act as an account authority for authentication. In this case LDAP user accounts should be configured with the pam_policy keyword set to ldap. This can be specified globally in the defaults file /etc/security/policy.conf.  Alternatively, if a proxyagent account credential is specified then the slapd server will act as a password repository and accounts will be authenticated locally on the client. These credentials can be shared with clients systems via ldapclient(8) so that the administrative tools I mentioned in my previous blog, useradm and the Oracle Solaris Account Manager, can be used to manage LDAP accounts.

The new Oracle Solaris Account Manager BUI is an optionally installed application that is integrated into the Solaris Dashboard. All of the Dashboard applications are based on webui(7) and Oracle's Javascript Extensible Toolkt (JET), which provides for accessibility and localization. To install the application follow these instructions. The Account Manager provides the same functionality as the new useradm application, which is an interactive python application using curses for screen management.


Both of these applications are unprivileged rad(8) clients. They provide remote administration by connecting to local or remote RAD servers. Two RAD modules, usermgr(3rad)and labelmgr(3rad), provides the underlying functionality. The man pages for these RAD modules are included in the webui-usermgr package. The security policies for account management are enforced in these RAD modules, not in the clients. Although the initial user account that is created during installation has the System Administrator rights profile, only a a subset of rights can be delegated to other accounts. These RAD clients only show the attributes that are may be delegated by the current user. Since useradm is started from the command line, it can be invoked after assuming the root role. But the Solaris Dashboard does not currently provide an interface for role assumption. So if you want to be able to assign arbitrary attributes to users and roles, you will need to login with a user account that has been assigned the authorization solaris.*.


The User Account Manager that is available with the beta release of Oracle Solaris 11.4 has a couple of bugs. The most serious bug needs to be addressed before using the application using the following workaround:


  1. After installing the webui-usermgr package, assume the root role
  2. cd /usr/lib/webui/htdocs/solaris/apps/usermgr/viewmodel
  3. Edit the file u_vm_addRemoveItems.js
  4. In line 265, change the pair of single quotes to a pair of square brackets. That is, change:   '');  to []);

This fix is necessary for checkboxes to be cleared when items are added to the account.

There is another bug with an easy workaround. When exiting the User Account Manager, you need to click the selection twice, since the first one isn't handled properly.


Another small bug may be visible the first time one of the label selection dialogs (Minimum Label or Clearance) is selected. If the radio buttons are not aligned properly, simply refresh the dialog by switching momentarily to the other label selection dialog, and then switching back. The following image shows how to assign the clearance to a user using the labels that I described in Protecting Sensitive Data in Oracle Solaris 11.4.




Here's the equivalent interface using useradm:



As the developer of these applications, I'd be interested in your feedback. But as I am now retired, Oracle support is now the responsible party.

Hi. I'm Glenn Faden, one of the architects for Oracle Solaris 11. Although I retired last year, my Oracle blog postings are still available, and Darren Moffat recently posted a new entry about Application Sandboxing. I also developed the new file and process labeling features which can be used to restrict access to sensitive data, which is a core requirement for every organization. Inadequate information classification and policy enforcement have contributed to embarrassing and costly data breaches. Administrators with root access have often been responsible for such data loss. Oracle Solaris 11.4 provides a set of unique access controls that can prevent processes, even with root privileges, from reading sensitive data.

The root account has traditionally been all powerful in UNIX systems. Oracle Solaris 8 introduced Role Based Access Control (RBAC) which made it possible to limit rootaccess to authorized users. Oracle Solaris 10 extended RBACwith a new privilege model that greatly reduced the need for root access. At the same time the concepts of basic privileges and the limit privilege set were introduced, enabling the Principle of Least Privilege to be applied to any process, even those running as root. Oracle Solaris 11 added immutable zones, making it possible to lock down the security policy configuration. Even a process with all privileges cannot modify an immutable configuration.

Oracle Solaris 11.4 adds the concept of data classification so that access is further restricted based on process clearance. This clearance policy supplements the existingDiscretionary Access Policy (DAC - based on users and groups), and the Solaris privilege policy. Although a process with sufficient privilege can override the DAC policy, there are no privileges to override the clearance policy. Users with sufficient clearance can apply sensitivity labels to ZFS file system objects and to IPC objects such as shared memory. Newly created files and directories automatically inherit the label of their parent directory. ZFS file systems and their snapshots are also automatically labeled with the maximum label of their contents. These labeled objects are only accessible to processes with sufficient clearance.

Process clearance is established at login time based on the user's RBAC attributes via Pluggable Authentication Modules (PAM). Although any process can lower its clearance, there is no interface by which a process can raise its clearance. Roles are also assigned clearances; when an authorized user assumes a role via su(8), the resulting process clearance is set to the minimum of the current user clearance and the role's clearance. Similarly, users with full sudo(8) access are still limited by their process clearance. Processes with insufficient clearance cannot observe,  trace, or debug other processes; nor can they observe or modify kernel memory.

Clearances are defined using labels whose components are configured via labelcfg(8) based on an organization's security policies.  The table below is based on the clearances that are specified in /etc/security/tsol/label_codings.compliance, which is further described here. It demonstrates how process clearances are reduced when switching to another user. Bob and Alice have each been granted the root role, but they have disjoint clearances. The label C Internal Use Only is the greatest lower bound (minimum label) that they share.



Using su or sudoto Bobto Aliceto root
from BobC Payment DataC Internal Use OnlyC Payment Data
from AliceC Internal Use OnlyC Health RecordsC Health Records
from rootC Payment DataC Health RecordsAdmin_High

Process clearances are also maintained by the Service Management Facility (SMF) which sets the specified or default clearance for each service. Only a few services need explicit clearances, such as those that assign clearances to user processes. Services such as login, ssh, and the Remote Access Daemon (RAD) are started with the maximum clearance.

Although a process cannot raise its own clearance, there are provisions for authorized users to instantiate new processes with an elevated clearance. These facilities include RBACprofiles, sandboxing, and the Trusted Path Domain.

Readers who are familiar with Trusted Solaris or its successor, Trusted Extensions, know that labeling has been an optional feature of Solaris for decades. In fact, the new labeling and clearance functionality shares much of its infrastructure with Trusted Extensions. However, Trusted Extensions enforces a more restrictive policy in which data labels must be preserved when data is moved or copied, even over the network. The new Oracle Solaris clearance policy is more flexible and does not prevent users with sufficient clearance from sharing labeled data with uncleared users. This flexibility is appropriate because the policy is enabled by default in Solaris 11.4. Its effects are generally transparent until clearances and labels are explicitly assigned to users and data.  Trusted Extensions remains an alternative policy which can be enabled using labeladm(8).

Filter Blog

By date: By tag: