Versions Compared

Key

  • This line was added.
  • This line was removed.
  • Formatting was changed.

Wiki Markup
The POSIX defines {{setuid()}} in a rather non-intuitive wayfunction has complex semantics and platform-specific behavior  \[[Open Group 04|AA. C References#Open Group 04]\]

If the process has appropriate privileges, setuid() shall set the real user ID, effective user ID, and the saved set-user-ID of the calling process to uid.

If the process does not have appropriate privileges, but uid is equal to the real user ID or the saved set-user-ID, setuid() shall set the effective user ID to uid; the real user ID and saved set-user-ID shall remain unchanged.

The phrase "appropriate privileges" varies from platform to platform. For example, on Solaris appropriate privileges means that EUID=0 (that is, the process is running as root). On BSD, it means that EUID=0 or that uid=geteuid(). On Linux, it means that the process has CAP_SETUID capability and that setuid(geteuid()) will fail if the effective EUID is not equal to 0, the RUID, or the SSUID.

Because of this complex behavior, there may be cases where the desired privilege drops are unsuccessful. For example, the range of Linux Kernel versions (2.2.0-2.2.15) is vulnerable to an insufficient privilege attack wherein setuid(getuid()) did not drop privileges as expected when the capability bits were set to zero. As a precautionary measure, subtle behavior and error conditions for the targeted implementation must be carefully noted.

...

Code Block
bgColor#ffcccc
/*  Code intended to run with elevated privileges   */

/* Temporarily Temporarydrop Dropprivileges */
if (seteuid(getuid()) != 0) {
  /* Handle Errorerror */
}

/*  Code intended to run with lower privileges  */ 

if (need_more_privileges) {
  /* Restore Privileges */
  if (seteuid(0) != 0) {
    /* Handle Error */
  }

  /*  Code intended to run with elevated privileges   */
}

/* ... */

/* Permanently Permanentdrop Dropprivileges */
if (setuid(getuid()) != 0) {
  /* Handle Error */
}

/*  Code intended to run with lower privileges  */ 

...