GLEXEC-2009-0003


Summary:

 

Any user that can run the glexec executable, and is in the white list of users allowed to run glexec, can obtain the contents of certain files that they do not have permission to access.


Component Vulnerable Versions Platform Availability Fix Available
glexec all all not known to be publicly available no
Status Access Required Host Type Required Effort Required Impact/Consequences
Verified local user in the glexec white list glexec high medium
Fixed Date Credit
n/a Jim Kupsch

Access Required:

local user in the glexec white list

This vulnerability requires local access to the machine with the ability to execute glexec. In addition the user must be in the white list of accounts permitted to use glexec.

Effort Required:

high

To exploit this vulnerability requires the ability to write some simple code, and to call glexec with a certain set of inputs. The attacker also needs to be in the white list of users authorized to use glexec. The effort is high because the attacker is required to win a race condition, which may be a rare event.

Impact/Consequences:

medium

This vulnerability allows the attacker to read the contents of files that the calling user would not normally have access, including files that should only be readable by root. If the server contains files of a very sensitive nature the impact of this vulnerability could be of a high consequence.

Full Details:

 

Glexec allows the user to copy an X.509 certificate from the caller's directory to a directory owned by the account that privileges are being switched to. The name of the source and destination file are specified by the user of glexec.

Precautions are taken in the code to make sure the source proxy is owned by the user executing glexec and the location where the proxy is written is owned by the user that glexec is switching to. The code contains a defect that allows a race condition to violate these precautions.

The writing of the proxy file is done correctly as it performed after the privileges of glexec are set to final privileges.

In version 0.5.40 and later, the user privileges are dropped, but the same problem exists with respect to group privileges is the glexec executable is setgid.

The reading of the proxy file contains the defect. The certificate is read when the effective user is the root user. When the effective user is root, all files in the system can be accessed irregardless of actual file permissions. An outline of the major steps taken to read the proxy in glexec_read_source_proxy are as follows:

  1. stat_value = stat( filename )
  2. glexec_check_proxy_file( stat_value )
    1. check owner is real user id
    2. check mode is not a link
    3. check permissions allow only the owner to read and write file and the file is a regular file
    4. check size of file is < GLEXEC_MAX_PROXY (200000)
  3. f = open( filename )
  4. fstat_value = fstat( f )
  5. check (dev, inode) of stat_value and fstat_value match
  6. read( f )

There are two problems with this code. The first is minor. The stat in step 1 should be lstat. Without this change the test to check if the object referred to by the path is not a symbolic link will never fail. If filename is a symbolic link stat always returns the information about the object referred to by the link instead of the link, while lstat returns information about the link itself. Checking for a link is unnecessary as an arbitrary file is allowed if it meets the other criteria and the user could just change the path to refer to the same file as symbolic link.

The second more serious problem is that the code is susceptible to a cryogenic sleep attack. A cryogenic sleep attack can occur when the file used in step 1 is different from the file used in step 3 (even though the dev and inode are the same). The user of glexec can specify a file that matches all the criteria of step 2, then stop the glexec process using a SIGSTOP signal between step 1 and step 3. The attacker now deletes the file and waits for a file containing sensitive data that reuses the same device and inode. At this point the process can be continued using the SIGCONT signal. The open and fstat return the matching device and inode, and glexec will read the sensitive data and write them into a file the attacker can then read.

This attack is somewhat limited in scope because the file to read must be created after step 1 occurs, the amount of data read is limited to 200,000 characters, the file to attack must be on the same device, the process must be stopped between steps 1 and 3, and the inode must be reused. These all minimize the likelihood of success, but do not decrease it to zero.

Cause:

failure to drop privileges
race condition

The cause of this problem is a time of check, time of use (TOCTOU) race condition between the stat and open calls in steps 2 and 4 respectively. Another cause is the properties of the file opened were not checked (the checks of step 2 should have been done on the fstat. Finally, the need for this type of code could be eliminated if the file was opened using the user's privilege instead of root's privilege.

Proposed Fix:

 

A simple fix for this problem is to modify the algorithm used to read the file to the outline below:

  1. set effective group id to real group id
  2. set effective user id to real user id
  3. f = open( filename )
  4. fstat_value = fstat( f )
  5. check owner is real user id
  6. check permissions allow group and other cannot read and write the file
  7. check size of file is < GLEXEC_MAX_PROXY (200000)
  8. read( f )

This code does not have the same flaws since only one file system object is accessed by the open and fstat is guaranteed to return the information for this file. Since the privilege level is dropped to the real user the ability to read unauthorized files is completely eliminated.

See How to Open a File and Not Get Hacked by Kupsch and Miller for an alternative method of dealing with the cryogenic sleep attack and library to open the file without being susceptible.

Acknowledgment:

 

This research funded in part by National Science Foundation grant OCI-0844219, NATO grant CLG 983049, and National Science Foundation grants CNS-0627501 and CNS-0716460.