pwauth
A Unix Web Authenticator
Author: Jan Wolter (E-Mail)
DOWNLOAD:
Stable version:
pwauth-2.3.6.tar.gz
Introduction:
Pwauth is an authenticator designed to be used with
mod_auth_external or
mod_authnz_external
and the Apache HTTP Daemon to support
reasonably secure web authentication out of the system password database on most
versions of Unix.
What pwauth actually does is very simple. Given a login and a password, it
returns a status code indicating whether it is a valid login/password or not.
It is normally installed as an suid-root program, so other programs (like
Apache or a CGI program) can run it to check if a login/password is valid
even though they don't themselves have read access to the system password
database.
Applications:
I have used pwauth in two major configurations:
- Basic Authentication.
This is the authentication system built into most browsers, where
the browser provides a pop-up login box asking the user for their
login/password and the authentication is negotiated between the
user's browser and the http daemon. This is relatively rarely used
on production websites these days.
In this configuration pwauth is
run by Apache through the mod_auth_external. It can be used to protect
both CGI programs and static documents. CGIs do not have to do any
authentication themselves - the name of the logged in users, if any,
is passed to them by Apache.
- Form-Based Authentication.
In most modern websites authentication is not handled by the http
daemon, but by the CGI programs running under it. In such cases,
the login/password input boxes generally appear on the web page, and
the data is passed to the CGI program, which does the check against
the user database itself. Usually after the inital login the CGI
program issues a session ID which is then sent back to the server with
each new page request, so that we can tell that the user is already
logged in.
In this configuration, pwauth would be run directly by the CGI.
Mod_auth_external is not needed.
The APIs for Unix authentication systems vary quite a lot, and pwauth
supports most of them. Major variations include:
- Direct system password database access.
This uses the low-level system interface to the password database to
check the password. Typically this means calling something like
getpwnam() to look the given login name up the database, and
then running crypt() on the given password to see if it matches
the value in the database. The exact system calls vary significantly
for different unix systems. Pwauth includes support for all
popular systems and some unpopular ones.
This is generally the best approach from a pure performance point of view.
- Login.conf authentication. (currently OpenBSD only)
Some versions of Unix, mainly the BSD versions, have a
"login.conf" file that can be used to configure authentication
for different classes of users. Among other things, the configuration
file specifies a program to be run to authenticate a user. For OpenBSD
only, version 2.3.0 of pwauth adds the ability to read the
login.conf file and authenticate users by the method specified
there. Though substantially slower than directly accessing the password
database, this configuration is useful if you are using unusual settings
in "login.conf" and want pwauth to comply with them.
- PAM authentication.
PAM (Portable Authentication Module) is a still higher level interface to
the authentication system supported by some versions of Unix (notably
Solaris, Linux and FreeBSD). With PAM there is a configuration file that
specifies the authentication requirements for different programs,
designating which dynamically loaded libraries to use to do the
authentication. Authentication from the system password database is
only one of many possibilities.
Another common application is to use the pam_smb module to do NT-style SMB
authentication.
Features:
Other configurable features of pwauth include:
- Lastlog support.
Many Unix systems maintain a lastlog file that keeps record of
the last login on each account. Pwauth can be configured to
update this on each successful authentication.
- Restrictions on calling process uid.
Pwauth can be configured to only work for uids on a short list.
Normally this would include only the uid that the HTTP daemon runs on.
It will decline to run for any other users.
This would mostly prevent users logged into the system from running the
program directly - not that it would give them any information that the
'su' or 'passwd' programs wouldn't give them,
but it is easier to interface a password guessing program
to pwauth than to those, so restricting who can run it is useful.
- Restrictions on authentiated uids.
Pwauth is normally configured to reject all attempts to log
into accounts with uids below some value.
This prevents it's use on system accounts.
- Understand expired logins and passwords.
Most versions of Unix today include mechanisms where by login IDs
can be set to expire after a certain date. There are also mechanisms
by which passwords can be made to expire, so that the account becomes
inaccessible if the password is not changed by that date.
Pwauth version 2.3.0 is configured by default
refuse all attempts to log into
accounts that have expired logins or passwords.
Of course, since it cannot send messages to the user, it cannot warn
of impending expirations. This would have to be done by your CGIs.
- Understand /etc/nologin.
On most Unix systems, if you create a file named /etc/nologin
then users will not be able to log in. The contents of the file are
displayed to them instead. Pwauth version 2.3.0 is configured
by default to refuse logins if that file exists,
though it cannot, of course, display the contents.
You can also configure it to use a different file, so that pwauth
authentications can be disabled separately from regular logins.
- Sequentialized sleep after bad logins.
Normally you don't want authentication programs to be too fast, because
that would allow people to zip through a dictionary of password guesses
very quickly.
Traditional Unix login programs sleep a bit before giving you a chance
to try another password after one has failed.
This is more complex to do with HTTP authentication because the user
doesn't need to wait for the response of the first one to make another
request - the same user can easily run many requests at the same time.
In the default configuration,
pwauth gets an exclusive lock on a file after every authentication
request. On successful authentications, it drops the lock immediately,
but on unsuccessful authentications it sleeps a few seconds before
dropping it. Under normal usage, this should have no noticable effect,
but after a failed authentication attempt, all pwauth
processes on the system will be held up for a couple seconds.
So even if a user tries barraging your system with password guesses,
he will get responses back no faster than one every couple seconds.
In the meantime, valid authentications could get very slow, and the
system will accumulate a large number of processes blocked on the lock
file. Admittedly not ideal. Maybe if I ever see this happen, I'll
implement some better behavior for that case.
- Failure logs.
Basically, a failure log keeps count of how many consecutive bad logins
are made, and on the next good login, reports the failure count, and
resets it to zero. It may also disable login attempts if some limit
is exceeded. Relatively few unix login programs do this,
but, starting with version 2.3.0, pwauth can support this even
if the regular login system does not.
At least, it does the part about incrementing the count on
bad logins and disabling accounts that exceed some limit. However
there is no path by which the pwauth could report the bad
login count to the user.
If you want to report failed logins, the pwauth distribution includes
a checkfaillog utility that can be run from a CGI after a
successful login to report the failed logins and reset the count to zero.
- Suppression of core dumps.
On some versions of Unix core dump files can be publically readable.
Since a core dump from pwauth would likely include a user's plain
text password and possibly fragments of the system password file,
this is undesirable. Pwauth disables core dumps.
Because in typical configurations pwauth is run very frequently
(on each HTTP request to a protected page), all configuration is compiled
in. This means it does not have to read and parse a configuration file
on every run, improving performance. It does mean that you need to recompile
pwauth every time you change it's configuration.
(But, of course, it does not have to be recompiled if the PAM or login.conf
configuration is changed.)
Security Considerations:
I believe that pwauth, with
mod_auth_external,
is the most secure method for doing web authentication
out of unix shadow password systems.
Mod_auth_pam or mod_auth_system can also do this, but since they
are internal authenticators, they will only work if you make the shadow
password file readable to the http server. This means that if there are any
exploitable vulnerabilities in the http server, then it may be possible for
people to grab a copy of your shadow password file.
Worse, any CGI program on your
system which is not run under suExec or cgiwrap also has read access to your
shadow password database, and any bugs in these might also expose your entire
password database. When
mod_auth_external
and pwauth are used, neither the
http server nor any CGI programs are given access to the shadow database.
Only the pwauth program does. Since it is a small and simple program,
it is much easier to assure that it does not have security weaknesses.
Having said that, web authentication from a Unix password file is an idea that
many sensible people find seriously questionable.
We developed it for use on a system whose security concerns are
seriously different,
and it has worked well for us over many years, in the face of fairly intense
hacker activity.
See Apache's
FAQ for a discussion of some of the issues here.
Pwauth has features that can address most of the arguments made here,
if correctly configured, but you need to be aware of the issues and
extremely careful.
A fundamental security problem with web authentication is that the
passwords are sent in clear text over the network. In the case of
basic authentication, they are sent with every page request. Furthermore,
with the http protocol, unlike a protocol like telnet, copies of passwords
are likely to be cached in various places along the way.
Though exploits based on this are rare, it is a fundamentally sloppy way
to treat a password.
I strongly recommend that pwauth be used
with the https protocol, which encrypts all requests including the passwords,
whenever possible.
When using form-based authentication there is another potential
security problem that has nothing directly to do with pwauth.
Typically in such systems you assign each successfully logged in user
a session ID, which they can use to identify themselves in future
http requests. This is either placed in a cookie, or passed from page
to page as a CGI query argument. If it is a cookie, or the query string
of a GET request, then it will be passed to the CGI program in an environment
variable. On most (but not all) Unix systems, any logged in user can see
the environment variables of any process running on the system.
This would make it possible to steal the session ID and impersonate the
user. Basic authentication does not have this problem, nor do query
arguments in POST requests (but few web sites use exclusively POST requests).
Mod_auth_external has two ways of
passing arguments to the external authenticator.
The "environment" method passes the user's login and password
via environment variables and has the same security problem as described
above.
It should never be used.
Use the "pipe" method instead.
This passes arguments securely.
Release Notes:
Versions of pwauth prior to version 2.2.8 were distributed as
part of the
mod_auth_external
package. Pwauth version 2.2.8 is identical to the version included
in the mod_auth_external version 2.2.8 release.
Later version numbers for the two packages diverged, retaining no
correspondence to each other.
Links
Here are some links to relevant software:
- Mod_Auth_External.
The Apache module that invokes pwauth in
basic authentication configurations.
- Mod_Authz_Unixgroup.
An Apache module that does unix group checking, for users who want to
restrict access by unix groups.
- Apache HTTP Server. Can't run
mod_auth_anything without it.
- mod_auth_shadow.
Can be used to authenticate out of a shadow password file, just as
mod_auth_external and pwauth can.
Seems to be a more recent reimplementation of the same concept.
- PAM.
Portable Authentication Modules are libraries that have a common interface
and can be linked to a program to do authentication out of different
databases. Linux, FreeBSD and Solaris support PAM. OpenBSD does not.
If you want to authenticate from a PAM module, but the user your httpd runs
as does not have the necessary access, then the pwauth external
authenticator can be run from mod_auth_external to do the PAM
authentication.
The list of
PAM modules includes authenticators for Kerberos, radius,
unix password or shadow files, SMB, various SQL databases, and just about
anything else imaginable.
- mod_auth_pam.
If you want to use a PAM module to authenticate, and whatever user apache
runs as has the necessary access to do the check, then you don't need
an external authenticator, and you should probably use this module instead
of mod_auth_external and pwauth.
Last Update:
Mon Dec 17 08:09:19 EST 2007