mod_privsep
Privilege Separation for Apache httpd

mod_privsep

Synopsis

mod_privsep addresses the problem of the Apache WebDAV (mod_dav) virtual server limitation of only being able to write files as a single user id (usually something like 'nobody' or 'www').

mod_privsep addresses this problem in a secure way by adding privilege separation to the Apache web server (conceptually similar to ssh privilege separation).

A privilege separated Apache can be used to allow WebDAV write access to users' home directories while both preserving and honouring unix permissions and allowing the use of unix quotas and PAM authentication.

Architecture

In Privilege Separation mode Apache continues to run as an unprivileged user although an additional secure process runs as 'root'.

The apache worker processes communicate with the 'root' privileged separated process via unix sockets to carry out system authentication and privileged file system operations. Namely:

Interfaces

APR file IO calls are modified to use the privsep versions which take an additional context argument (privsep_token_t*):

The privsep versions use a token fetched from from r->notes. If the privsep token exists then the request is dispatched to the privilege separated daemon, otherwise the file IO method is executed directly in the regular way.

One special case exists for the apr_stat calls made from ap_directory_walk. This is called before map_to_storage has been done and any authentication hooks run. This special case needs the apr_stat calls to be executed as root to know if the path actually exists. The security leak potential is minimised by making apr_stat the only call that is able to be made as uid 0 and ap_directory_walk is the only routine that calls ap_privsep_stat with the special ap_preauth_stat_token.

Portability

mod_privsep has been tested on Linux and FreeBSD.

apr interfaces have been used where possible but mod_privsep relies on unix sockets (socketpair,sendmsg,recvmsg) and the ability to send file descriptors over unix sockets. It also currently depends on PAM.

It should be relatively easily ported to other unix-like OS.

NOTE: the opendir implementation relies on platform specific details. Specifically, that directories can be opened as file descriptors and also that the file descriptor is the first structure member of the private DIR* structure (changed to fdopendir in latest patch).

It is potentially possible to implement this feature for Windows as a preliminary investigation shows that it is possible to pass file handles between processes. More investigation is needed.

Building

  # apply patch

  # run buildconf to pick up configure.in change
  ./buildconf

  ./configure \
    --enable-dav \
    --enable-privsep \
    --enable-authn-privsep

Configuration

  # Output error log messages for privileged accesses
  LogLevel info
  PrivilegeSeparationDebug On

  <Directory "/opt/apache2.2/uploads/">

    # Enable WebDAV and privilege separation for this directory
    Dav On
    PrivilegeSeparation On

    # System authentication through privilege separated PAM
    AuthType Basic
    AuthName DAV-upload
    AuthBasicProvider privsep

    Options Indexes
    AllowOverride None
    Require valid-user

    # Workaround for WebDAV PROPFIND bug on dirs with index files
    DirectoryIndex /no_directory_index

  </Directory>

Design Issues

Credits