Pubcookie login cgi

Included on this page:

Introduction

The Pubcookie login server has two primary functions: to authenticate users and to issue authentication tokens (granting cookies) consumed by Pubcookie-enabled target application servers. Authentication occurs either by checking user-provided credentials via a backend authentication service (Kerberos, SecurID, ...) or by verifying a token that was created on a previous visit to the login server. Example code to interface to an authentication system is provided.

Implementation

The Pubcookie login server uses a CGI program to handle all HTTP requests. This CGI program, hereafter referred to as "the login cgi" or index.cgi, is compiled from C and is the central Pubcookie component. The login cgi displays the web page where users are asked to enter authentication credentials as well as other web pages that display error messages.

Due to the important nature of the Pubcookie login server, the only other services that should be run on the same system are those which receive an equally high level of scrutiny for security. As deployed at the University of Washington, the Pubcookie login server is powered by the Apache web server software. Other web server software which supports CGI and SSL should also work, but this supposition has not been tested.

Authentication services

The login cgi has a very simple interface for talking to backend authentication services.

Most sites will want to use the "basic" login flavor, which supports username/paassword single-sign-on authentication. (Currently no other flavors exist!)

The basic login flavor supports many different verifiers. Some of the ones shipped with pubcookie as of this writing are:

You can set which verifier to be used with the "basic_verifier" configuration parameter (see Run-time configuration). Some verifiers will allow or require further customization; see the section referring to that verifier.

Apache Configuration

Choosing the location of your login page

Depending on your installation environment you may choose to install the login server in a number of configurations. Two general models are presented here with any necessary Apache configuration directives.

Specifying the login URL as a directory

For a clean looking login URL you can install the login server to be the default file in a directory. The default filename, index.cgi, is a common name for a cgi file that would be executed when only directory URL is specified.

The University of Washington uses https://weblogin.washington.edu/ as the login server URL; it's very simple for users to identify in the browser's URL field.

The Apache config directive 'DirectoryIndex' tells Apache it how to handle requests for directories. See the mod_dir documentation for more information. When a request is made for a directory Apache will choose the first file it finds in the DirectoryIndex list.

Our DirectoryIndex line looks something like:

DirectoryIndex index.html index.cgi

If this is the configuration you choose, make sure there isn't an index.html file in the same directory as the index.cgi binary.

Explicit specification of login CGI

The login CGI is not name dependant and can be deployed as index.cgi, login.cgi, or some other CGI file if you like. In can also be put in any subdirectory you wish.

Your login server's URL could be something like https://www.example.edu/cgi-bin/login.cgi. Some sites may do this avoid the confusion with the default index page.

Depending how you want to configure things with Apache or which ever Web server you want to use for the login server, your login server URL could be something like https://www.myuniversity.edu/login where /login is mapped to the CGI program (index.cgi or whatever you rename it to).

The default login server and login URI are specified as "login_host" and "login_uri" in pubcookie configuration file. (Individual applications may override what login server they refer to with the PubCookieLogin directive in their apache configuration file, but this isn't recommended.)

Apache configuration directive you might have to tweak

Apache needs to know how to identify and handle cgi scripts. Some distributions of Apache will hav the cgi handler disabled, you will want to make sure the following line is in your httpd.conf and not commented out.

AddHandler cgi-script .cgi

Build the Pubcookie login server

This has been made easier with autoconf. (Thanks Jon Miner, University of Wisconsin!) To build a barebones login server, run:

$ ./configure --enable-login --disable-apache
$ make
$ make install

This sequence will build and install the index.cgi, keyserver, and keyclient binaries, using the default directory prefix (/usr/local/pubcookie, henceforth called {PUBCOOKIE_DIR}) and "alwaystrue" verifier.

To build the login server with other verifiers enabled (e.g. "kerberos_v5", "ldap", or "shadow") look at the configure options and adjust accordingly:

$ ./configure --help

Run-time configuration

Most configuration of the login server can be done at run-time via Pubcookie's config file. It is located at {PUBCOOKIE_DIR}/config and has "attr: value" lines throughout. A sample configuration file is included as config.sample. A complete explanation of all available options is available in the config documentation.

Some of the more notable variables are:

debug
An integer. A non-zero value enables debug logging. The higher the number, the more debugging output that is generated.
login_host
the hostname of login server
login_uri
the complete URI of the login cgi
enterprise_domain
the domain under which all hosts will live. must be at least a second level domain (e.g. example.edu)
basic_verifier
the verifier to use for the "basic" flavor
keymgt_uri
the location of the "keyserver" CGI. See the Key Management section.

The following options should refer to the same files that your web server uses for SSL.

ssl_key_file
the location of the SSL key
ssl_cert_file
the location of the SSL certificate

If your institution uses a single CA without any intermediate certificates, set ssl_ca_file to the path of the CA's certificate. If your institution uses multiple CAs or intermediate certificates, you'll need a directory (ssl_ca_path) contain those certificates named via their OpenSSL hashes. At least one of ssl_ca_file and ssl_ca_path should be specified.

ssl_ca_file
the location of a single CA
ssl_ca_path
a directory containing files named after their OpenSSL hash

See config.html for a full list of attributes.

Localization

The design of the login cgi preceded consideration of external use of Pubcookie, so there is much work to be done to improve flexibility and make it less specific to the University of Washington.

However, preliminary work has been done with login templates (specifying the look of each page the login CGI serves up) and the run-time configuration file. These pages should live in {PUBCOOKIE_DIR}/login_templates. We recommend you start with the files in src/login_templates.generic/ and customize them as you see fit. The Washington and CMU files (or an older version of them) is supplied for your amusement in src/login_templates.uw and src/login_templates.cmu respectively.

More configuration: User agent blocking via ok_browsers file

The {PUBCOOKIE_DIR}/ok_browsers file contains a list of acceptable browsers. The idea behind ok_browsers is to block browsers that either have a known security flaw (i.e. don't forget cookies when they should) or don't work with Pubcookie (i.e. Opera which doesn't do domain level cookie scoping correctly). IE and Netscape are the only two browser families that are known to work with Pubcookie.

So far we've been too chicken to really use the 'ok_browsers' functionality to block browsers that we know don't work. For now our ok_browsers has a single line: "Mozilla". Since both Netscape and IE claim to be Mozilla that covers the only two browsers known to work with Pubcookie. Proceed according to your own policy.

Key management

{PUBCOOKIE_DIR}/keys is the location of the keystore that the login cgi uses. The login cgi makes use of several different keys.

Generate or reuse keypairs for the login server

The pubcookie_login key and certificate are used to secure the "login cookie" that maintains the single sign-on session with the login server. These files are kept exclusively on the login server. We recommend that you reuse your existing private key and SSL server certificate rather than generating a new keypair. The login cgi will automatically do so if you set ssl_cert_file and ssl_key_file correctly.

Generate granting keypair for authentication assertions

Next, the pubcookie_granting keypair is needed to secure authentication assertions sent from login server to application servers, as represented by the "granting cookie". The key is kept exclusively on the login server; the certificate must be distributed to every application server.

$ openssl req -new -x509 -nodes \
    -out /usr/local/pubcookie/keys/pubcookie_granting.cert \
    -newkey rsa:1024 -keyout /usr/local/pubcookie/keys/pubcookie_granting.key

If you want to place these files in a different location (than {PUBCOOKIE_DIR}/keys/pubcookie_granting.{key,cert}), you'll need to set the granting_cert_file and granting_key_file attributes.

Configure keyserver on the login server

keyserver is a program that maintains DES keys. Unfortunately, due to subtleties in the key usage constraints, it is unable to run as a CGI underneath a login server. Instead, we recommend that it be run from inetd.

Add a line like the following to the login server's /etc/inetd.conf:

2222    stream  tcp     nowait  root    /usr/local/pubcookie/bin/keyserver keyserver

where /usr/local/pubcookie/bin/keyserver is where the keyserver binary is installed. Make sure that your pubcookie/config file is correctly configured.

If you are using xinetd, you should create a file named keyserver in /etc/xinetd.d with the following contents:

# description: pubcookie keyserver
service keyserver
{
	type			= UNLISTED
	protocol		= tcp
	port			= 2222
	disable			= no
	socket_type		= stream
	wait			= no
	user			= root
	group			= tty
	server			= /usr/local/pubcookie/bin/keyserver
}

After adding this line (or file), restart inetd.

Generate a DES key for the login server with keyclient

Now run keyclient to generate a DES key for the login server:

% /usr/local/pubcookie/bin/keyclient

This will cause the keyserver program to generate a new DES key for the login server to use to provide confidentiality for the login cookies.

Generating DES keys for the application servers with keyclient

Generating DES keys for the application servers is just as easy as above---in fact, the exact same command works.

It is important that the application server's SSL certicate is signed by the same certificate authority as is configured in the login server's config file.

Remember that the application server will also need a correct 'config' file.

Upgrading

Upgrading from pre-3.0 pubcookie

Advanced configuration

Redundant login servers
Redundant application hosts

Sites frequently want several hosts configured identically to provide redundancy (either for performance or stability). In this section, we're assuming that you have a set of machines with an identical SSL certificate and key on them.

For instance, an institution might have 15 webmail servers named webmail1.example.edu through webmail15.example.edu with 15 unique IP addresses. All of them are equipped with a webmail.example.edu certificate and are behind a Cisco Load Director which controls the IP address for webmail.example.edu.

Use keyclient on webmail1.example.edu to generate a webmail.example.edu DES key. Use keyclient -d on all other webmail machines (webmail2.example.edu, etc.) to download an identical application key to the remaining servers.

Security considerations

Login server security
don't run anything else on it: anyone who can add content to the login server can steal all cookies
Application server security
Handling secrets
Other stuff

Old Tools That Might Be Handy for Debugging

pbc_create creates a pubcookie cookie, convenient for creating cookies ad hoc. Arguments come in via stdin and the cookie is put out on stdout. Args are space delimited, and in order: user appsrvid appid type creds serial crypt_file cert_key_file. Anything too big is just truncated, no support for defaults or anything like that. See src for details.

pbc_verify decrypts/verifies/displays pubcookie cookies, convenient for 'unbundling' a cookie and seeing what's inside. The arguments come in on the command line, the cookie comes in on stdid, and the contents are dumped to stdout. The required argument is cookie_type and the optional arguments are encryption_key and cert_file.

As an example you can use these two programs to do things like:

# echo "willey appsrvid appid 1 2 23 \
    /usr/local/pubcookie/c_key /usr/local/pubcookie/test.key" | \
    ./pbc_create | \
    ./pbc_verify 1 /usr/local/pubcookie/c_key /usr/local/pubcookie/test.cert

and get something like

user: willey
version: a5
type: 1
creds: 2
serial: 23
appsrvid: appsrvid
appid: appid
create_ts: 1006986719
last_ts: 1006986719

Copyright 1999-2002, University of Washington. All rights reserved.
See doc/LICENSE.txt for terms of use.

$Id: install-login.html,v 1.3 2002/10/02 21:41:00 dors Exp $