FreeBSD’s kernel provides quite sophisticated privilege model that extends the traditional UNIX user-and-group one. Here I’ll show how to leverage it to grant access to specific privileges to group of non-root users.
mac(9)
allows creating pluggable modules with policies that can extend existing base system security
definitions. struct mac_policy_ops
consist of many entry points that we can use to amend the behaviour.
This time, I wanted to grant a privilege to change realtime priority to a selected group. While Linux kernel lets you specify a named group, FreeBSD doesn’t have such ability, hence I created this very simple policy.
The privilege check can be extended using two user supplied functions: priv_check and priv_grant. The first one can be used to further restrict existing privileges, i.e. you can disallow some specific priv to be used in jails, etc. The second one is used to explicitly grant extra privileges not available for the target in base configuration.
The core of the mac_rtprio
module is dead simple. I defined sysctl tree for two oids: enable (on/off switch for the
policy) and gid (the GID target has to be member of), then I specified our custom version of mpo_priv_grant
called rtprio_priv_grant
. Body of my granting function is even simpler. If the policy is disabled or the privilege
that is being checked is not PRIV_SCHED_RTPRIO
, we simply skip and return EPERM
. If the user is member of the
designated group we return 0 that’ll allow the action - target would change realtime privileges.
Full source code of the module is available on GitHub.