RJ Systems
Linux System Administration
Home Tech Linux Links Consulting







Valid XHTML 1.0!

Valid CSS!

IPv6 test

PAM configuration guide for Debian

Introduction

In the past, programs for logging into a console, or the X Window System, had to be modified to support every new authentication method that was introduced. To remedy this situation, a framework was developed in the 1990s by Sun Microsystems' SunSoft development group, called Pluggable Authentication Modules (PAM). Basically a suite of shared libraries, it provides an abstraction layer between, on the one hand the various methods available that provide authentication, such as passwords, smartcards and biometrics, and on the other hand the applications that require authentication and would otherwise have to support those methods directly. With PAM, all that is necessary for these components to cooperate is that a specific PAM module be available for each of them.

This page explains how Linux-PAM is configured on systems running Debian GNU/Linux, although most all of it will apply to other distributions as well. It is meant to support other pages on this site that cover subjects such as OpenLDAP and Kerberos.


1. Service type

PAM is configured by defining a set of rules that can be stacked to combine the functions of various modules in order to complete a given authentication task. Originally, all PAM rules were defined in a single configuration file, /etc/pam.conf. This file can still be used, in which case each rule has up to five fields:

service-type	module-type	control		module-path	arguments

The service type usually matches the name of the service (see /etc/services) or application making the call to PAM, thus allowing certain modules to be applied to them. Valid service types can be, for example, login, su, sshd, or xdm, although other is used as a default.

Later it became possible to use a directory instead. Now, if /etc/pam.d/ is present, which is the default for Debian lenny, PAM will ignore /etc/pam.conf and instead search the directory for a filename that matches the name of the service or application making the call. Usually, these configuration files have almost the same syntax as before:

module-type	control		module-path	arguments

2. Module type

The module type, or task, is the management group that the rule corresponds to. Any particular PAM module will support up to four different types:

auth Authentication and authorization. The user's identity is established by matching their login name and password against a source, resulting in success or failure. Group memberships and other priviledges are also granted.
account Account management. Often implemented to restrict or permit access to a service according to, e.g. time of day, available resources, membership of the wheel group, or location.
password Password management. Required for updating a user's authentication token. There is usually one module for each challenge/response-based authentication type.
session Session management. Performs required tasks for users before and after they use a service, e.g. logging, or mounting directories.


3. Control

The control field determines how PAM will behave when a module fails. There are two different syntaxes available for it: a simple one that uses a single directive, and a more complex one that uses a set of value=action pairs. The simple syntax includes four possible directives:

required Causes the entire stack to fail if the module's demands are not met, but only after the entire stack has been processed.
requisite Idem, except that when the module fails control is returned directly to the application. Often used to provide an extra measure of security.
sufficient Success of the module is enough to satisfy the requirements of an entire stack, after which no other modules will be processed. If it fails, the process will move on to the next rule.
optional The result from this module is only important if it is the only one in the stack.

The more complex syntax uses a square-bracketed selection of value=action pairs:

[value1=action1 value2=action2 ...]

The values are module return codes, possible valid choices for which are:

abortCritical error (module "fail now" request).
acct_expiredUser account expired.
auth_errAuthentication failure.
authinfo_unavailUnderlying authentication service cannot retrieve authentication information.
authtok_disable_agingAuthentication token aging disabled.
authtok_errAuthentication token manipulation error.
authtok_expiredAuthentication token expired.
authtok_lock_busyAuthentication token lock busy.
authtok_recover_errAuthentication information cannot be recovered.
bad_itemBad item passed to pam_*_item().
buf_errMemory buffer error.
conv_againConversation function is event driven and data is not available yet.
conv_errConversation error.
cred_errFailure setting user credentials.
cred_expiredUser credentials expired.
cred_insufficientCannot access authentication data due to insufficient credentials.
cred_unavailUser credentials unavailable; the underlying authentication service cannot retrieve them.
defaultImplies all values not mentioned explicitly.
ignoreIgnore underlying account module regardless of whether the control flag is required, optional, or sufficient.
incompletePlease call this function again to complete authentication stack. Before calling again, verify that conversation is completed.
maxtriesAn authentication service has maintained a retry count which has been reached. No further retries should be attempted.
module_unknownThe module is unknown.
new_authtok_reqdNew authentication token required. This is normally returned if the machine security policies require that the password should be changed, either because the password is NULL, or because it has aged.
no_module_dataNo module specific data is present.
open_errThe module could not be loaded.
perm_deniedPermission denied.
service_errError in service module.
session_errCannot make or remove an entry for the specified session.
successSuccessful function return.
symbol_errSymbol not found.
system_errSystem error.
try_againPreliminary check by password service.
user_unknownUser not known to the underlying authenticaiton module.

The actions can either be unsigned integers, indicating the number of modules in the stack to jump over next, or be one of the following keywords:

ignore The module's return status will not influence the final result unless there are no other modules in the stack.
bad The module's return status should indicate a module failure. If it is the first failure, this return status will be used for the entire stack.
die Idem, except that the stack also terminates and control is immediately returned to the application.
ok The return code will override a previous success state of the stack, but not a previous failure state.
done Idem, except that the stack also terminates and control is immediately returned to the application.
reset Clear the stack's memory and start again with the next stacked module.

To illustrate how this syntax is used, each of the four simple control directives mentioned above can be replaced with an equivalent complex expression:

required = [ success=ok new_authtok_reqd=ok ignore=ignore default=bad ]
requisite = [ success=ok new_authtok_reqd=ok ignore=ignore default=die ]
sufficient = [ success=done new_authtok_reqd=done default=ignore ]
optional = [ success=ok new_authtok_reqd=ok default=ignore ]


4. Module path

The module path is either the full filename of the module, beginning with a "/", or a pathname that is relative to the default module directory, which is /lib/security/ on a Debian lenny system. In practice, this usually means that only the names of the modules are mentioned.

The modules themselves are all named as pam_<name>.so. See the Linux-PAM System Administrator's Guide (linked below) for a list of all standard modules, their descriptions and possible arguments.


5. Arguments

The last field is a space-separated list of tokens that can be used to modify the behavior of a module. Any arguments are usually found in the documentation for the module (e.g. man pam_unix). If an argument includes one or more spaces, it should surrounded by square brackets.

Some modules go further and even have their own dedicated configuration files.


6. Include statements

Linux-PAM also includes two relatively new keywords that are usually described as control directives − even in the Linux-PAM System Administrator's Guide − but are actually quite different:

include Includes all lines of the same module type found in an additional configuration file, the name of which is specified as an argument.
substack Idem, except that evaluation of the done and die actions in a substack do not cause PAM to skip the rest of the stack (only the substack), jumps cannot escape the substack process (the substack is treated as a single module), and the reset action will only return the entire stack to the state it was in when the substack evaluation started.

As might be expected, the syntax for their use is a little different as well:

module-type	keyword		file-path

Here, the file path is either the full name of the file, beginning with a "/", or a pathname that is relative to the /etc/pam.d/ directory.

Previously, Linux-PAM did not provide any include methods. To compensate for this lack of basic functionality, some distributions followed a solution adopted by RedHat, which was to use a module, called pam_stack.so. A complicated patch, it was basically a kludge that hijacked PAM's internals to obtain a pass over an additional configuration file.

At first, Debian used pam_stack.so also, but later switched to a more elegant patch that achieves essentially the same result. The syntax for it is:

@include	file-path

These statements are still used in Debian lenny, even though it is now possible to replaced them with native PAM include statements that are both more efficient and more flexible. Therefore, one might expect that this Debian patch will eventually be phased out.


7. Debian 5.0 defaults

On Debian 5.0 (lenny) systems, every PAM service configuration file contains between one and four @include statements. This is because Debian lenny uses four configuration files − one for each of the four module types − to apply the same system defaults to all service types. It is a much more efficient solution than having to edit all of the individual service configuration files every time a general change is required. The five system default configuration files are:

  • /etc/pam.d/common-auth
  • /etc/pam.d/common-account
  • /etc/pam.d/common-password
  • /etc/pam.d/common-session

System administrators are expected to edit only these four files. When configuring certain network applications, doing so is mandatory. In such cases, it is good to know what the default configurations are for these files. Here is an overview, followed by a few explanations:

/etc/pam.d/common-auth:

auth		required	pam_unix.so	nullok_secure

/etc/pam.d/common-account:

account		required	pam_unix.so

/etc/pam.d/common-password:

password	required	pam_unix.so	nullok obscure md5

/etc/pam.d/common-session:

session		required	pam_unix.so

The default employs only a single PAM module, pam_unix.so, which is used for standard Unix authentication, retrieving and setting account information, and changing passwords. This module has many possible arguments, four of which are used here:

md5 Encrypt new passwords with the MD5 algorithm.
nullok Allow users to access services even if their password is blank.
nullok_secure Idem, as long as PAM_TTY equals one of the values found in /etc/securetty.
obscure Enable some extra checks on password strength.

The last two arguments are not mentioned in the Linux-PAM System Administrator's Guide, but are described in the Debian man page for pam_unix, along with many other options.


8. Debian 6.0 defaults

On Debian 6.0 (squeeze) systems, every PAM service configuration file contains between one and five @include statements. This is because Debian squeeze uses five configuration files: one for each of the first three module types and two files for the fourth. This is to apply the same system defaults to all service types. It is a much more efficient solution than having to edit all of the individual service configuration files every time a general change is required. The five system default configuration files are:

  • /etc/pam.d/common-auth
  • /etc/pam.d/common-account
  • /etc/pam.d/common-password
  • /etc/pam.d/common-session
  • /etc/pam.d/common-session-noninteractive

The last file is new with Debian squeeze, its purpose being to allow those session modules that do not provide shell-like interactive capabilities for users (e.g. cron, cups, samba, ppp) to be separated from those that do (e.g. login, ssh, gdm). This way, it can be avoided that certain modules are called unnecessarily for certain services in certain contexts.

All of these files now include a structure that is a bit more complex than it was previously with Debian lenny:

  1. A primary block of per-package modules.
  2. A fallback module for if no primary-block module succeeds.
  3. A module to prime the stack with a positive return value.
  4. An optional additional block of per-package modules.

The primary block consists of one or more PAM modules associated with various applications. The fallback is a module that always denys access in case none of the primary block modules succeed. The stack is then primed to permit access with a module that always results in a positive return value. This is to avoid an error code being returned in case a success code has not already been set. Finally, an additional block of one or more modules may follow.

System administrators are expected to alter only these five files. However, as of PAM v1.0.1-6, the default is to manage these files with pam-auth-update. This Perl script is used to configure PAM using the pre-defined profiles that come with PAM module packages. Nevertheless, it is good to know what the default configurations are for these files in case manual intervention is needed anyway. Here is an overview, followed by a few explanations:

/etc/pam.d/common-auth:

auth		[success=1 default=ignore]				pam_unix.so nullok_secure
auth		requisite						pam_deny.so
auth		required						pam_permit.so

/etc/pam.d/common-account:

account		[success=1 new_authtok_reqd=done default=ignore]	pam_unix.so
account		requisite						pam_deny.so
account		required						pam_permit.so

/etc/pam.d/common-password:

password	[success=1 default=ignore]				pam_unix.so obscure sha512
password	requisite						pam_deny.so
password	required						pam_permit.so

/etc/pam.d/common-session:

session		[default=1]						pam_permit.so
session		requisite						pam_deny.so
session		required						pam_permit.so
session		required						pam_unix.so

/etc/pam.d/common-session-noninteractive:

session		[default=1]						pam_permit.so
session		requisite						pam_deny.so
session		required						pam_permit.so
session		required						pam_unix.so

As opposed to the PAM configuration files in Debian 5.0 (lenny), here the first three files are configured so that the correct return values are more likely to be given, rather than when this is left up to the pam_unix.so module alone, or any other module(s) that might be used along with it or in its place.

In each of these three cases, depending on the response from the pam_unix.so module, the second module, pam_deny.so, will either be skipped or not. If it is, the next and last module to be processed will be pam_permit.so, which always permits access. If it is not skipped, pam_deny.so will not only deny access, but because of the requisite directive, control will immediately be returned to the application before pam_permit.so is ever reached.

The default configuration employs three different PAM modules. The first, pam_unix.so, is used for standard Unix authentication, retrieving and setting account information, and changing passwords. This module has many possible arguments, three of which are used here:

sha512 Encrypt new passwords with the SHA512 algorithm. If this is not recognized by the crypt function, it falls back to MD5.
nullok_secure Allow users to access services even if their password is blank, but only as long as PAM_TTY equals one of the values found in /etc/securetty.
obscure Enable some extra checks on password strength.

The last two arguments are not mentioned in the Linux-PAM System Administrator's Guide, but are described in the Debian man page for pam_unix, along with many other options.


9. See also
10. Further reading
  • Samar V, Schemers R. 1995. RFC 86.0 − Unified Login with Pluggable Authentication Modules (PAM). Open Software Foundation. Text at The Open Group.

11. Sources
  • Carter G. 2003. LDAP System Administration. O'Reilly & Associates, Inc. ISBN 1-56592-491-6. 294 pp.
  • Garman J. 2003. Kerberos, The Definitive Guide. O'Reilly & Associates, Inc. ISBN-13 978-0-596-00403-3. 253 pp.
  • Leeuw D. 2012. PAM Explanation. HTML at PIG: Practical Interoperability Guides.
  • Milicchio F, Gehrke WA. 2007. Distributed Services with OpenAFS. Springer-Verlag. ISBN-13 978-3-540-36633-1. 395 pp.
  • Morgan AG. 2001. Pluggable Authentication Modules (PAM). Open-PAM working group. Text at The Kernel Archives.
  • Morgan AG, Kukuk T. 2010. The Linux-PAM System Administrator's Guide. HTML at The Kernel Archives..
  • Pettenò D. 2008. Linux-PAM 0.99 upgrade guide. HTML at Gentoo Linux.


Last modified: 2014-02-15, 23:03

©2003-2014 RJ Systems. Permission is granted to copy, distribute and/or modify the
content of this page under the terms of the OpenContent License, version 1.0.