To check authorizations, use the chkauthattr(3SECDB) library function, which verifies whether or not
a user has a given authorization. The synopsis is:
|
int chkauthattr(const char *authname, const char *username);
|
The chkauthattr() function checks the policy.conf(4), user_attr(4), and prof_attr(4) databases in order for a
match to the given authorization.
If you are modifying existing code that tests for root UID, you should
find the test in the code and replace it with the chkauthattr() function. A typical root UID check is shown in the first code
segment below. An authorization check replacing it is shown in the second
code segment; it uses the solaris.jobs.admin authorization
and a variable called real_login representing the user. Example 1. Standard root check
|
|
ruid = getuid();
if ((eflag || lflag || rflag) && argc == 1) {
if ((pwp = getpwnam(*argv)) == NULL)
crabort(INVALIDUSER);
if (ruid != 0) {
if (pwp->pw_uid != ruid)
crabort(NOTROOT);
else
pp = getuser(ruid);
} else
pp = *argv++;
} else {
|
|
Example 2. Authorization check
|
|
ruid = getuid();
if ((pwp = getpwuid(ruid)) == NULL)
crabort(INVALIDUSER);
strcpy(real_login, pwp->pw_name);
if ((eflag || lflag || rflag) && argc == 1) {
if ((pwp = getpwnam(*argv)) == NULL)
crabort(INVALIDUSER);
if (!chkauthattr("solaris.jobs.admin", real_login)) {
if (pwp->pw_uid != ruid)
crabort(NOTROOT);
else
pp = getuser(ruid);
} else
pp = *argv++;
} else {
|
|
For new applications, find an appropriate location for the test and
use chkauthattr() as shown above. Typically the authorization
check makes an access decision based on the identity of the calling user
to determine if a privileged action (for example, a system call) should
be taken on behalf of that user.
Applications that perform a test to restrict who can perform their
security-relevant functionality are generally setuid
to root. Programs that were written prior to RBAC and that are only available
to the root user may not have such checks. In most cases, the kernel requires
an effective user ID of root to override policy enforcement.
Therefore, authorization checking is most useful in programs that are setuid to root.
For instance, if you want to write a program that allows authorized
users to set the system date, the command must be run with an effective
user ID of root. Typically, this means that the file
modes for the file would be -rwsr-xr-x with root ownership.
Use caution, though, when making programs setuid
to root. For example, the effective UID should be set
to the real UID as early as possible in the program's
initialization function. The effective UID can then be
set back to root after the authorization check is performed and before the
system call is made. On return from the system call, the effective UID should
be set back to the real UID again to adhere to the principle
of least privilege.
Another consideration is that LD_LIBRARY path is
ignored for setuid programs (see SECURITY section in ld.so.1(1)) and that shell scripts
must be modified to work properly when the effective and real UIDs are different. For example, the -p flag in
Bourne shell is required to avoid resetting the effective UID
back to the real UID.
Using an effective UID of root instead of the real UID requires extra care when writing shell scripts. For example,
many shell scripts check to see if the user is root before executing their
functionality. With RBAC, these shell scripts may be running with the effective UID of root and with a real UID of a user or
role. Thus, the shell script should check euid instead
of uid. For example,
|
WHO=`id | cut -f1 -d" "`
if [ ! "$WHO" = "uid=0(root)" ]
then
echo "$PROG: ERROR: you must be super-user to run this script."
exit 1
fi
|
should be changed to
|
WHO=`/usr/xpg4/bin/id -n -u`
if [ ! "$WHO" = "root" ]
then
echo "$PROG: ERROR: you are not authorized to run this script."
exit 1
fi
|
Authorizations can be explicitly checked in shell scripts by piping
the output of the auths(1)
utility to grep(1).
For example,
|
AUTHS=`auths`
echo $AUTHS|grep "^solaris.date$"
if [ $? -ne 0 ]
then
echo "$PROG: ERROR: you are not authorized to set the date."
exit 1
fi
|
|