1
<!doctype linuxdoc system>
5
$Id: pam_modules.sgml,v 1.4 2002/09/15 20:44:05 hartmans Exp $
7
Copyright (c) Andrew G. Morgan 1996-2001. All rights reserved.
9
** some sections, in this document, were contributed by other
10
** authors. They carry individual copyrights.
12
Redistribution and use in source and binary forms, with or without
13
modification, are permitted provided that the following conditions are
16
1. Redistributions of source code must retain the above copyright
17
notice, and the entire permission notice in its entirety,
18
including the disclaimer of warranties.
20
2. Redistributions in binary form must reproduce the above copyright
21
notice, this list of conditions and the following disclaimer in the
22
documentation and/or other materials provided with the distribution.
24
3. The name of the author may not be used to endorse or promote
25
products derived from this software without specific prior
28
ALTERNATIVELY, this product may be distributed under the terms of the
29
GNU General Public License, in which case the provisions of the GNU
30
GPL are required INSTEAD OF the above restrictions. (This clause is
31
necessary due to a potential bad interaction between the GNU GPL and
32
the restrictions contained in a BSD-style copyright.)
34
THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED
35
WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
36
MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
37
IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
38
INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
39
BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
40
OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
41
ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
42
TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE
43
USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH
50
<title>The Linux-PAM Module Writers' Guide
51
<author>Andrew G. Morgan, <tt>morgan@kernel.org</tt>
52
<date>DRAFT v0.76 2002/05/09
54
This manual documents what a programmer needs to know in order to
55
write a module that conforms to the <bf/Linux-PAM/ standard. It also
56
discusses some security issues from the point of view of the module
68
#include <security/pam_modules.h>
70
gcc -fPIC -c pam_module-name.c
71
ld -x --shared -o pam_module-name.so pam_module-name.o
78
<bf/Linux-PAM/ (Pluggable Authentication Modules for Linux) is a
79
library that enables the local system administrator to choose how
80
individual applications authenticate users. For an overview of the
81
<bf/Linux-PAM/ library see the <bf/Linux-PAM/ System Administrators'
85
A <bf/Linux-PAM/ module is a single executable binary file that can be
86
loaded by the <bf/Linux-PAM/ interface library. This PAM library is
87
configured locally with a system file, <tt>/etc/pam.conf</tt>, to
88
authenticate a user request via the locally available authentication
89
modules. The modules themselves will usually be located in the
90
directory <tt>/usr/lib/security</tt> and take the form of dynamically
91
loadable object files (see dlopen(3)). Alternatively, the modules can
92
be statically linked into the <bf/Linux-PAM/ library; this is mostly to
93
allow <bf/Linux-PAM/ to be used on platforms without dynamic linking
94
available, but the two forms can be used together. It is the
95
<bf/Linux-PAM/ interface that is called by an application and it is
96
the responsibility of the library to locate, load and call the
97
appropriate functions in a <bf/Linux-PAM/-module.
100
Except for the immediate purpose of interacting with the user
101
(entering a password etc..) the module should never call the
102
application directly. This exception requires a "conversation
103
mechanism" which is documented below.
105
<sect>What can be expected by the module
108
Here we list the interface that the conventions that all
109
<bf/Linux-PAM/ modules must adhere to.
111
<sect1>Getting and setting <tt/PAM_ITEM/s and <em/data/
114
First, we cover what the module should expect from the <bf/Linux-PAM/
115
library and a <bf/Linux-PAM/ <em/aware/ application. Essesntially this
116
is the <tt/libpam.*/ library.
125
extern int pam_set_data(pam_handle_t *pamh,
126
const char *module_data_name,
128
void (*cleanup)(pam_handle_t *pamh,
129
void *data, int error_status) );
134
The modules may be dynamically loadable objects. In general such files
135
should not contain <tt/static/ variables. This and the subsequent
136
function provide a mechanism for a module to associate some data with
137
the handle <tt/pamh/. Typically a module will call the
138
<tt/pam_set_data()/ function to register some data under a (hopefully)
139
unique <tt/module_data_name/. The data is available for use by other
140
modules too but <em/not/ by an application.
143
The function <tt/cleanup()/ is associated with the <tt/data/ and, if
144
non-<tt/NULL/, it is called when this data is over-written or
145
following a call to <tt/pam_end()/ (see the Linux-PAM Application
149
The <tt/error_status/ argument is used to indicate to the module the
150
sort of action it is to take in cleaning this data item. As an
151
example, Kerberos creates a ticket file during the authentication
152
phase, this file might be associated with a data item. When
153
<tt/pam_end()/ is called by the module, the <tt/error_status/
154
carries the return value of the <tt/pam_authenticate()/ or other
155
<tt/libpam/ function as appropriate. Based on this value the Kerberos
156
module may choose to delete the ticket file (<em/authentication
157
failure/) or leave it in place.
160
The <tt/error_status/ may have been logically OR'd with either of the
161
following two values:
165
<tag><tt/PAM_DATA_REPLACE/</tag>
166
When a data item is being replaced (through a second call to
167
<tt/pam_set_data()/) this mask is used. Otherwise, the call is assumed
168
to be from <tt/pam_end()/.
170
<tag><tt/PAM_DATA_SILENT/</tag>
171
Which indicates that the process would prefer to perform the
172
<tt/cleanup()/ quietly. That is, discourages logging/messages to the
185
extern int pam_get_data(const pam_handle_t *pamh,
186
const char *module_data_name,
192
This function together with the previous one provides a method of
193
associating module-specific data with the handle <tt/pamh/. A
194
successful call to <tt/pam_get_data/ will result in <tt/*data/
195
pointing to the data associated with the <tt/module_data_name/. Note,
196
this data is <em/not/ a copy and should be treated as <em/constant/
200
Note, if there is an entry but it has the value <tt/NULL/, then this
201
call returns <tt/PAM_NO_MODULE_DATA/.
210
extern int pam_set_item(pam_handle_t *pamh,
217
This function is used to (re)set the value of one of the
218
<tt/item_type/s. The reader is urged to read the entry for this
219
function in the <bf/Linux-PAM/ application developers' manual.
222
In addition to the <tt/item/s listed there, the module can set the
223
following two <tt/item_type/s:
227
<tag><tt/PAM_AUTHTOK/</tag>
229
The authentication token (often a password). This token should be
230
ignored by all module functions besides <tt/pam_sm_authenticate()/ and
231
<tt/pam_sm_chauthtok()/. In the former function it is used to pass the
232
most recent authentication token from one stacked module to
233
another. In the latter function the token is used for another
234
purpose. It contains the currently active authentication token.
236
<tag><tt/PAM_OLDAUTHTOK/</tag>
238
The old authentication token. This token should be ignored by all
239
module functions except <tt/pam_sm_chauthtok()/.
244
Both of these items are reset before returning to the application.
245
When resetting these items, the <bf/Linux-PAM/ library first writes
246
<tt/0/'s to the current tokens and then <tt/free()/'s the associated
250
The return values for this function are listed in the
251
<bf>Linux-PAM</bf> Application Developers' Guide.
260
extern int pam_get_item(const pam_handle_t *pamh,
267
This function is used to obtain the value of the specified
268
<tt/item_type/. It is better documented in the <bf/Linux-PAM/
269
Application Developers' Guide. However, there are three things worth
274
Generally, if the module wishes to obtain the name of the user, it
275
should not use this function, but instead perform a call to
276
<tt/pam_get_user()/ (see section <ref id="pam-get-user"
280
The module is additionally privileged to read the authentication
281
tokens, <tt/PAM_AUTHTOK/ and <tt/PAM_OLDAUTHTOK/ (see the section
282
above on <tt/pam_set_data()/).
285
The module should <em/not/ <tt/free()/ or alter the data pointed to by
286
<tt/*item/ after a successful return from <tt/pam_get_item()/. This
287
pointer points directly at the data contained within the <tt/*pamh/
288
structure. Should a module require that a change is made to the this
289
<tt/ITEM/ it should make the appropriate call to <tt/pam_set_item()/.
292
<sect2>The <em/conversation/ mechanism
295
Following the call <tt>pam_get_item(pamh,PAM_CONV,&item)</tt>, the
296
pointer <tt/item/ points to a structure containing an a pointer to a
297
<em/conversation/-function that provides limited but direct access to
298
the application. The purpose of this function is to allow the module
299
to prompt the user for their password and pass other information in a
300
manner consistent with the application. For example, an X-windows
301
based program might pop up a dialog box to report a login
302
failure. Just as the application should not be concerned with the
303
method of authentication, so the module should not dictate the manner
304
in which input (output) is obtained from (presented to) to the user.
307
<bf>The reader is strongly urged to read the more complete description of
308
the <tt/pam_conv/ structure, written from the perspective of the
309
application developer, in the <bf/Linux-PAM/ Application Developers'
313
The return values for this function are listed in the
314
<bf>Linux-PAM</bf> Application Developers' Guide.
317
The <tt/pam_response/ structure returned after a call to the
318
<tt/pam_conv/ function must be <tt/free()/'d by the module. Since the
319
call to the conversation function originates from the module, it is
320
clear that this <tt/pam_response/ structure could be either statically
321
or dynamically (using <tt/malloc()/ etc.) allocated within the
322
application. Repeated calls to the conversation function would likely
323
overwrite static memory, so it is required that for a successful
324
return from the conversation function the memory for the response
325
structure is dynamically allocated by the application with one of the
326
<tt/malloc()/ family of commands and <em/must/ be <tt/free()/'d by the
330
If the <tt/pam_conv/ mechanism is used to enter authentication tokens,
331
the module should either pass the result to the <tt/pam_set_item()/
332
library function, or copy it itself. In such a case, once the token
333
has been stored (by one of these methods or another one), the memory
334
returned by the application should be overwritten with <tt/0/'s, and
337
There is a handy macro <tt/_pam_drop_reply()/ to be found in
338
<tt><security/_pam_macros.h></tt> that can be used to
339
conveniently cleanup a <tt/pam_response/ structure. (Note, this
340
include file is specific to the Linux-PAM sources, and whilst it will
341
work with Sun derived PAM implementations, it is not generally
344
<sect2>Getting the name of a user<label id="pam-get-user">
350
extern int pam_get_user(pam_handle_t *pamh,
357
This is a <bf/Linux-PAM/ library function that returns the
358
(prospective) name of the user. To determine the username it does the
359
following things, in this order:
362
<item> checks what <tt/pam_get_item(pamh, PAM_USER, ... );/ would have
363
returned. If this is not <tt/NULL/ this is what it returns. Otherwise,
365
<item> obtains a username from the application via the <tt/pam_conv/
366
mechanism, it prompts the user with the first non-<tt/NULL/ string in
370
<item> The <tt/prompt/ argument passed to the function
371
<item> What is returned by <tt/pam_get_item(pamh,PAM_USER_PROMPT, ... );/
372
<item> The default prompt: ``Please enter username: ''
378
By whatever means the username is obtained, a pointer to it is
379
returned as the contents of <tt/*user/. Note, this memory should
380
<em/not/ be <tt/free()/'d by the module. Instead, it will be liberated
381
on the next call to <tt/pam_get_user()/, or by <tt/pam_end()/ when the
382
application ends its interaction with <bf/Linux-PAM/.
385
Also, in addition, it should be noted that this function sets the
386
<tt/PAM_USER/ item that is associated with the <tt/pam_[gs]et_item()/
390
The return value of this function is one of the following:
393
<item> <tt/PAM_SUCCESS/ - username obtained.
395
<item> <tt/PAM_CONV_AGAIN/ - converstation did not complete and the
396
caller is required to return control to the application, until such
397
time as the application has completed the conversation process. A
398
module calling <tt/pam_get_user()/ that obtains this return code,
399
should return <tt/PAM_INCOMPLETE/ and be prepared (when invoked the
400
next time) to recall <tt/pam_get_user()/ to fill in the user's name,
401
and then pick up where it left off as if nothing had happened. This
402
procedure is needed to support an event-driven application programming
405
<item> <tt/PAM_CONV_ERR/ - the conversation method supplied by the
406
application failed to obtain the username.
410
<sect2>Setting a Linux-PAM environment variable
416
extern int pam_putenv(pam_handle_t *pamh, const char *name_value);
421
<bf/Linux-PAM/ comes equipped with a series of functions for
422
maintaining a set of <em/environment/ variables. The environment is
423
initialized by the call to <tt/pam_start()/ and is <bf/erased/ with a
424
call to <tt/pam_end()/. This <em/environment/ is associated with the
425
<tt/pam_handle_t/ pointer returned by the former call.
428
The default environment is all but empty. It contains a single
429
<tt/NULL/ pointer, which is always required to terminate the
430
variable-list. The <tt/pam_putenv()/ function can be used to add a
431
new environment variable, replace an existing one, or delete an old
436
<item>Adding/replacing a variable<newline>
438
To add or overwrite a <bf/Linux-PAM/ environment variable the value of
439
the argument <tt/name_value/, should be of the following form:
442
name_value="VARIABLE=VALUE OF VARIABLE"
445
Here, <tt/VARIABLE/ is the environment variable's name and what
446
follows the `<tt/=/' is its (new) value. (Note, that <tt/"VARIABLE="/
447
is a valid value for <tt/name_value/, indicating that the variable is
450
<item> Deleting a variable<newline>
452
To delete a <bf/Linux-PAM/ environment variable the value of
453
the argument <tt/name_value/, should be of the following form:
456
name_value="VARIABLE"
459
Here, <tt/VARIABLE/ is the environment variable's name and the absence
460
of an `<tt/=/' indicates that the variable should be removed.
465
In all cases <tt/PAM_SUCCESS/ indicates success.
467
<sect2>Getting a Linux-PAM environment variable
473
extern const char *pam_getenv(pam_handle_t *pamh, const char *name);
478
This function can be used to return the value of the given
479
variable. If the returned value is <tt/NULL/, the variable is not
482
<sect2>Listing the Linux-PAM environment
488
extern char * const *pam_getenvlist(pam_handle_t *pamh);
493
This function returns a pointer to the entire <bf/Linux-PAM/
494
environment array. At first sight the <em/type/ of the returned data
495
may appear a little confusing. It is basically a <em/read-only/ array
496
of character pointers, that lists the <tt/NULL/ terminated list of
497
environment variables set so far.
500
Although, this is not a concern for the module programmer, we mention
501
here that an application should be careful to copy this entire array
502
before executing <tt/pam_end()/ otherwise all the variable information
503
will be lost. (There are functions in <tt/libpam_misc/ for this
504
purpose: <tt/pam_misc_copy_env()/ and <tt/pam_misc_drop_env()/.)
506
<sect1>Other functions provided by <tt/libpam/
508
<sect2>Understanding errors
514
<tt>extern const char *pam_strerror(pam_handle_t *pamh, int errnum);</tt>
517
This function returns some text describing the <bf/Linux-PAM/ error
518
associated with the argument <tt/errnum/. If the error is not
519
recognized <tt/``Unknown Linux-PAM error''/ is returned.
523
<sect2>Planning for delays
529
<tt>extern int pam_fail_delay(pam_handle_t *pamh, unsigned int
533
This function is offered by <bf/Linux-PAM/ to facilitate time delays
534
following a failed call to <tt/pam_authenticate()/ and before control
535
is returned to the application. When using this function the module
536
programmer should check if it is available with,
539
#ifdef PAM_FAIL_DELAY
541
#endif /* PAM_FAIL_DELAY */
546
Generally, an application requests that a user is authenticated by
547
<bf/Linux-PAM/ through a call to <tt/pam_authenticate()/ or
548
<tt/pam_chauthtok()/. These functions call each of the <em/stacked/
549
authentication modules listed in the <bf/Linux-PAM/ configuration
550
file. As directed by this file, one of more of the modules may fail
551
causing the <tt/pam_...()/ call to return an error. It is desirable
552
for there to also be a pause before the application continues. The
553
principal reason for such a delay is security: a delay acts to
554
discourage <em/brute force/ dictionary attacks primarily, but also
555
helps hinder <em/timed/ (cf. covert channel) attacks.
558
The <tt/pam_fail_delay()/ function provides the mechanism by which an
559
application or module can suggest a minimum delay (of <tt/micro_sec/
560
<em/micro-seconds/). <bf/Linux-PAM/ keeps a record of the longest time
561
requested with this function. Should <tt/pam_authenticate()/ fail,
562
the failing return to the application is delayed by an amount of time
563
randomly distributed (by up to 25%) about this longest value.
566
Independent of success, the delay time is reset to its zero default
567
value when <bf/Linux-PAM/ returns control to the application.
571
<sect>What is expected of a module
574
The module must supply a sub-set of the six functions listed
575
below. Together they define the function of a <bf/Linux-PAM
576
module/. Module developers are strongly urged to read the comments on
577
security that follow this list.
582
The six module functions are grouped into four independent management
583
groups. These groups are as follows: <em/authentication/,
584
<em/account/, <em/session/ and <em/password/. To be properly defined,
585
a module must define all functions within at least one of these
586
groups. A single module may contain the necessary functions for
587
<em/all/ four groups.
589
<sect2> Functional independence
592
The independence of the four groups of service a module can offer
593
means that the module should allow for the possibility that any one of
594
these four services may legitimately be called in any order. Thus, the
595
module writer should consider the appropriateness of performing a
596
service without the prior success of some other part of the module.
599
As an informative example, consider the possibility that an
600
application applies to change a user's authentication token, without
601
having first requested that <bf/Linux-PAM/ authenticate the user. In
602
some cases this may be deemed appropriate: when <tt/root/ wants to
603
change the authentication token of some lesser user. In other cases it
604
may not be appropriate: when <tt/joe/ maliciously wants to reset
605
<tt/alice/'s password; or when anyone other than the user themself
606
wishes to reset their <em/KERBEROS/ authentication token. A policy for
607
this action should be defined by any reasonable authentication scheme,
608
the module writer should consider this when implementing a given
611
<sect2> Minimizing administration problems
614
To avoid system administration problems and the poor construction of a
615
<tt>/etc/pam.conf</tt> file, the module developer may define all
616
six of the following functions. For those functions that would not be
617
called, the module should return <tt/PAM_SERVICE_ERR/ and write an
618
appropriate message to the system log. When this action is deemed
619
inappropriate, the function would simply return <tt/PAM_IGNORE/.
621
<sect2> Arguments supplied to the module
624
The <tt/flags/ argument of each of the following functions can be
625
logically OR'd with <tt/PAM_SILENT/, which is used to inform the
626
module to not pass any <em/text/ (errors or warnings) to the
630
The <tt/argc/ and <tt/argv/ arguments are taken from the line
631
appropriate to this module---that is, with the <em/service_name/
632
matching that of the application---in the configuration file (see the
633
<bf/Linux-PAM/ System Administrators' Guide). Together these two
634
parameters provide the number of arguments and an array of pointers to
635
the individual argument tokens. This will be familiar to C programmers
636
as the ubiquitous method of passing command arguments to the function
637
<tt/main()/. Note, however, that the first argument (<tt/argv[0]/) is
638
a true argument and <bf/not/ the name of the module.
640
<sect1> Authentication management
643
To be correctly initialized, <tt/PAM_SM_AUTH/ must be <tt/#define/'d
644
prior to including <tt><security/pam_modules.h></tt>. This will
645
ensure that the prototypes for static modules are properly declared.
651
<tt>PAM_EXTERN int pam_sm_authenticate(pam_handle_t *pamh, int flags,
652
int argc, const char **argv);</tt>
655
This function performs the task of authenticating the user.
658
The <tt/flags/ argument can be a logically OR'd with <tt/PAM_SILENT/
659
and optionally take the following value:
662
<tag><tt/PAM_DISALLOW_NULL_AUTHTOK/</tag>
663
return <tt/PAM_AUTH_ERR/ if the database of authentication
664
tokens for this authentication mechanism has a <tt/NULL/ entry for the
665
user. Without this flag, such a <tt/NULL/ token will lead to a success
666
without the user being prompted.
670
Besides <tt/PAM_SUCCESS/ return values that can be sent by this
671
function are one of the following:
675
<tag><tt/PAM_AUTH_ERR/</tag>
676
The user was not authenticated
677
<tag><tt/PAM_CRED_INSUFFICIENT/</tag>
678
For some reason the application does not have sufficient
679
credentials to authenticate the user.
680
<tag><tt/PAM_AUTHINFO_UNAVAIL/</tag>
681
The modules were not able to access the authentication
682
information. This might be due to a network or hardware failure etc.
683
<tag><tt/PAM_USER_UNKNOWN/</tag>
684
The supplied username is not known to the authentication
686
<tag><tt/PAM_MAXTRIES/</tag>
687
One or more of the authentication modules has reached its
688
limit of tries authenticating the user. Do not try again.
693
<tt>PAM_EXTERN int pam_sm_setcred(pam_handle_t *pamh, int flags, int
694
argc, const char **argv);</tt>
697
This function performs the task of altering the credentials of the
698
user with respect to the corresponding authorization
699
scheme. Generally, an authentication module may have access to more
700
information about a user than their authentication token. This
701
function is used to make such information available to the
702
application. It should only be called <em/after/ the user has been
703
authenticated but before a session has been established.
706
Permitted flags, one of which, may be logically OR'd with
710
<tag><tt/PAM_ESTABLISH_CRED/</tag>
711
Set the credentials for the authentication service,
712
<tag><tt/PAM_DELETE_CRED/</tag>
713
Delete the credentials associated with the authentication service,
714
<tag><tt/PAM_REINITIALIZE_CRED/</tag>
715
Reinitialize the user credentials, and
716
<tag><tt/PAM_REFRESH_CRED/</tag>
717
Extend the lifetime of the user credentials.
721
Prior to <bf/Linux-PAM-0.75/, and due to a deficiency with the way the
722
<tt/auth/ stack was handled in the case of the setcred stack being
723
processed, the module was required to attempt to return the same error
724
code as <tt/pam_sm_authenticate/ did. This was necessary to preserve
725
the logic followed by libpam as it executes the stack of
726
<em/authentication/ modules, when the application called either
727
<tt/pam_authenticate()/ or <tt/pam_setcred()/. Failing to do this,
728
led to confusion on the part of the System Administrator.
731
For <bf/Linux-PAM-0.75/ and later, libpam handles the credential stack
732
much more sanely. The way the <tt/auth/ stack is navigated in order to
733
evaluate the <tt/pam_setcred()/ function call, independent of the
734
<tt/pam_sm_setcred()/ return codes, is exactly the same way that it
735
was navigated when evaluating the <tt/pam_authenticate()/ library
736
call. Typically, if a stack entry was ignored in evaluating
737
<tt/pam_authenticate()/, it will be ignored when libpam evaluates the
738
<tt/pam_setcred()/ function call. Otherwise, the return codes from
739
each module specific <tt/pam_sm_setcred()/ call are treated as
743
Besides <tt/PAM_SUCCESS/, the module may return one of the following
747
<tag><tt/PAM_CRED_UNAVAIL/</tag>
748
This module cannot retrieve the user's credentials.
749
<tag><tt/PAM_CRED_EXPIRED/</tag>
750
The user's credentials have expired.
751
<tag><tt/PAM_USER_UNKNOWN/</tag>
752
The user is not known to this authentication module.
753
<tag><tt/PAM_CRED_ERR/</tag>
754
This module was unable to set the credentials of the user.
758
these, non-<tt/PAM_SUCCESS/, return values will typically lead to the
759
credential stack <em/failing/. The first such error will dominate in
760
the return value of <tt/pam_setcred()/.
764
<sect1> Account management
767
To be correctly initialized, <tt/PAM_SM_ACCOUNT/ must be
768
<tt/#define/'d prior to including <tt><security/pam_modules.h></tt>.
769
This will ensure that the prototype for a static module is properly
776
<tt>PAM_EXTERN int pam_sm_acct_mgmt(pam_handle_t *pamh, int flags, int
777
argc, const char **argv);</tt>
780
This function performs the task of establishing whether the user is
781
permitted to gain access at this time. It should be understood that
782
the user has previously been validated by an authentication
783
module. This function checks for other things. Such things might be:
784
the time of day or the date, the terminal line, remote
788
This function may also determine things like the expiration on
789
passwords, and respond that the user change it before continuing.
792
Valid flags, which may be logically OR'd with <tt/PAM_SILENT/, are the
793
same as those applicable to the <tt/flags/ argument of
794
<tt/pam_sm_authenticate/.
797
This function may return one of the following errors,
801
<tag><tt/PAM_ACCT_EXPIRED/</tag>
802
The user is no longer permitted access to the system.
803
<tag><tt/PAM_AUTH_ERR/</tag>
804
There was an authentication error.
805
<tag><tt/PAM_AUTHTOKEN_REQD/</tag>
806
The user's authentication token has expired. Before calling
807
this function again the application will arrange for a new one to be
808
given. This will likely result in a call to <tt/pam_sm_chauthtok()/.
809
<tag><tt/PAM_USER_UNKNOWN/</tag>
810
The user is not known to the module's account management
817
<sect1> Session management
820
To be correctly initialized, <tt/PAM_SM_SESSION/ must be
821
<tt/#define/'d prior to including
822
<tt><security/pam_modules.h></tt>. This will ensure that the
823
prototypes for static modules are properly declared.
826
The following two functions are defined to handle the
827
initialization/termination of a session. For example, at the beginning
828
of a session the module may wish to log a message with the system
829
regarding the user. Similarly, at the end of the session the module
830
would inform the system that the user's session has ended.
833
It should be possible for sessions to be opened by one application and
834
closed by another. This either requires that the module uses only
835
information obtained from <tt/pam_get_item()/, or that information
836
regarding the session is stored in some way by the operating system
837
(in a file for example).
843
<tt>PAM_EXTERN int pam_sm_open_session(pam_handle_t *pamh, int flags, int
844
argc, const char **argv);</tt>
847
This function is called to commence a session. The only valid, but
848
optional, flag is <tt/PAM_SILENT/.
851
As a return value, <tt/PAM_SUCCESS/ signals success and
852
<tt/PAM_SESSION_ERR/ failure.
855
<tt>PAM_EXTERN int pam_sm_close_session(pam_handle_t *pamh, int flags, int
856
argc, const char **argv);</tt>
859
This function is called to terminate a session. The only valid, but
860
optional, flag is <tt/PAM_SILENT/.
863
As a return value, <tt/PAM_SUCCESS/ signals success and
864
<tt/PAM_SESSION_ERR/ failure.
868
<sect1> Password management
871
To be correctly initialized, <tt/PAM_SM_PASSWORD/ must be
872
<tt/#define/'d prior to including <tt><security/pam_modules.h></tt>.
873
This will ensure that the prototype for a static module is properly
880
<tt>PAM_EXTERN int pam_sm_chauthtok(pam_handle_t *pamh, int flags, int
881
argc, const char **argv);</tt>
884
This function is used to (re-)set the authentication token of the
885
user. A valid flag, which may be logically OR'd with <tt/PAM_SILENT/,
886
can be built from the following list,
889
<tag><tt/PAM_CHANGE_EXPIRED_AUTHTOK/</tag>
890
This argument indicates to the module that the users
891
authentication token (password) should only be changed if it has
892
expired. This flag is optional and <em/must/ be combined with one of
893
the following two flags. Note, however, the following two options are
894
<em/mutually exclusive/.
896
<tag><tt/PAM_PRELIM_CHECK/</tag>
897
This indicates that the modules are being probed as to their
898
ready status for altering the user's authentication token. If the
899
module requires access to another system over some network it should
900
attempt to verify it can connect to this system on receiving this
901
flag. If a module cannot establish it is ready to update the user's
902
authentication token it should return <tt/PAM_TRY_AGAIN/, this
903
information will be passed back to the application.
905
<tag><tt/PAM_UPDATE_AUTHTOK/</tag>
906
This informs the module that this is the call it should change
907
the authorization tokens. If the flag is logically OR'd with
908
<tt/PAM_CHANGE_EXPIRED_AUTHTOK/, the token is only changed if it has
914
Note, the <bf/Linux-PAM/ library calls this function twice in
915
succession. The first time with <tt/PAM_PRELIM_CHECK/ and then, if the
916
module does not return <tt/PAM_TRY_AGAIN/, subsequently with
917
<tt/PAM_UPDATE_AUTHTOK/. It is only on the second call that the
918
authorization token is (possibly) changed.
921
<tt/PAM_SUCCESS/ is the only successful return value, valid
925
<tag><tt/PAM_AUTHTOK_ERR/</tag>
926
The module was unable to obtain the new authentication token.
928
<tag><tt/PAM_AUTHTOK_RECOVER_ERR/</tag>
929
The module was unable to obtain the old authentication token.
931
<tag><tt/PAM_AUTHTOK_LOCK_BUSY/</tag>
932
Cannot change the authentication token since it is currently
935
<tag><tt/PAM_AUTHTOK_DISABLE_AGING/</tag>
936
Authentication token aging has been disabled.
938
<tag><tt/PAM_PERM_DENIED/</tag>
941
<tag><tt/PAM_TRY_AGAIN/</tag>
942
Preliminary check was unsuccessful. Signals an immediate return
943
to the application is desired.
945
<tag><tt/PAM_USER_UNKNOWN/</tag>
946
The user is not known to the authentication token changing
953
<sect>Generic optional arguments
956
Here we list the generic arguments that all modules can expect to
957
be passed. They are not mandatory, and their absence should be
958
accepted without comment by the module.
962
<tag><tt/debug/</tag>
964
Use the <tt/syslog(3)/ call to log debugging information to the system
967
<tag><tt/no_warn/</tag>
969
Instruct module to not give warning messages to the application.
971
<tag><tt/use_first_pass/</tag>
973
The module should not prompt the user for a password. Instead, it
974
should obtain the previously typed password (by a call to
975
<tt/pam_get_item()/ for the <tt/PAM_AUTHTOK/ item), and use that. If
976
that doesn't work, then the user will not be authenticated. (This
977
option is intended for <tt/auth/ and <tt/passwd/ modules only).
979
<tag><tt/try_first_pass/</tag>
981
The module should attempt authentication with the previously typed
982
password (by a call to <tt/pam_get_item()/ for the <tt/PAM_AUTHTOK/
983
item). If that doesn't work, then the user is prompted for a
984
password. (This option is intended for <tt/auth/ modules only).
986
<tag><tt/use_mapped_pass/</tag>
988
<bf/WARNING:/ coding this functionality may cause the module writer to
989
break <em/local/ encryption laws. For example, in the U.S. there are
990
restrictions on the export computer code that is capable of strong
991
encryption. It has not been established whether this option is
992
affected by this law, but one might reasonably assume that it does
993
until told otherwise. For this reason, this option is not supported
994
by any of the modules distributed with <bf/Linux-PAM/.
996
The intended function of this argument, however, is that the module
997
should take the existing authentication token from a previously
998
invoked module and use it as a key to retrieve the authentication
999
token for this module. For example, the module might create a strong
1000
hash of the <tt/PAM_AUTHTOK/ item (established by a previously
1001
executed module). Then, with logical-exclusive-or, use the result as a
1002
<em/key/ to safely store/retrieve the authentication token for this
1003
module in/from a local file <em/etc/. .
1005
<tag><tt/expose_account/</tag>
1008
In general the leakage of some information about user accounts is not
1009
a secure policy for modules to adopt. Sometimes information such as
1010
users names or home directories, or preferred shell, can be used to
1011
attack a user's account. In some circumstances, however, this sort of
1012
information is not deemed a threat: displaying a user's full name when
1013
asking them for a password in a secured environment could also be
1014
called being 'friendly'. The <tt/expose_account/ argument is a
1015
standard module argument to encourage a module to be less discrete
1016
about account information as it is deemed appropriate by the local
1021
<sect>Programming notes
1024
Here we collect some pointers for the module writer to bear in mind
1025
when writing/developing a <bf/Linux-PAM/ compatible module.
1027
<sect1>Security issues for module creation
1029
<sect2>Sufficient resources
1032
Care should be taken to ensure that the proper execution of a module
1033
is not compromised by a lack of system resources. If a module is
1034
unable to open sufficient files to perform its task, it should fail
1035
gracefully, or request additional resources. Specifically, the
1036
quantities manipulated by the <tt/setrlimit(2)/ family of commands
1037
should be taken into consideration.
1042
Generally, the module may wish to establish the identity of the user
1043
requesting a service. This may not be the same as the username
1044
returned by <tt/pam_get_user()/. Indeed, that is only going to be the
1045
name of the user under whose identity the service will be given. This
1046
is not necessarily the user that requests the service.
1049
In other words, user X runs a program that is setuid-Y, it grants the
1050
user to have the permissions of Z. A specific example of this sort of
1051
service request is the <em/su/ program: user <tt/joe/ executes
1052
<em/su/ to become the user <em/jane/. In this situation X=<tt/joe/,
1053
Y=<tt/root/ and Z=<tt/jane/. Clearly, it is important that the module
1054
does not confuse these different users and grant an inappropriate
1058
The following is the convention to be adhered to when juggling
1063
<item>X, the identity of the user invoking the service request.
1064
This is the user identifier; returned by the function <tt/getuid(2)/.
1066
<item>Y, the privileged identity of the application used to grant the
1067
requested service. This is the <em/effective/ user identifier;
1068
returned by the function <tt/geteuid(2)/.
1070
<item>Z, the user under whose identity the service will be granted.
1071
This is the username returned by <tt/pam_get_user(2)/ and also stored
1072
in the <bf/Linux-PAM/ item, <tt/PAM_USER/.
1074
<item><bf/Linux-PAM/ has a place for an additional user identity that
1075
a module may care to make use of. This is the <tt/PAM_RUSER/ item.
1076
Generally, network sensitive modules/applications may wish to set/read
1077
this item to establish the identity of the user requesting a service
1078
from a remote location.
1083
Note, if a module wishes to modify the identity of either the <tt/uid/
1084
or <tt/euid/ of the running process, it should take care to restore
1085
the original values prior to returning control to the <bf/Linux-PAM/
1088
<sect2>Using the conversation function
1090
Prior to calling the conversation function, the module should reset
1091
the contents of the pointer that will return the applications
1092
response. This is a good idea since the application may fail to fill
1093
the pointer and the module should be in a position to notice!
1096
The module should be prepared for a failure from the conversation. The
1097
generic error would be <tt/PAM_CONV_ERR/, but anything other than
1098
<tt/PAM_SUCCESS/ should be treated as indicating failure.
1100
<sect2>Authentication tokens
1103
To ensure that the authentication tokens are not left lying around the
1104
items, <tt/PAM_AUTHTOK/ and <tt/PAM_OLDAUTHTOK/, are not available to
1105
the application: they are defined in
1106
<tt><security/pam_modules.h></tt>. This is ostensibly for
1107
security reasons, but a maliciously programmed application will always
1108
have access to all memory of the process, so it is only superficially
1109
enforced. As a general rule the module should overwrite
1110
authentication tokens as soon as they are no longer needed.
1111
Especially before <tt/free()/'ing them. The <bf/Linux-PAM/ library is
1112
required to do this when either of these authentication token items
1116
Not to dwell too little on this concern; should the module store the
1117
authentication tokens either as (automatic) function variables or
1118
using <tt/pam_[gs]et_data()/ the associated memory should be
1119
over-written explicitly before it is released. In the case of the
1120
latter storage mechanism, the associated <tt/cleanup()/ function
1121
should explicitly overwrite the <tt/*data/ before <tt/free()/'ing it:
1127
* An example cleanup() function for releasing memory that was used to
1131
int cleanup(pam_handle_t *pamh, void *data, int error_status)
1145
<sect1>Use of <tt/syslog(3)/
1148
Only rarely should error information be directed to the user. Usually,
1149
this is to be limited to ``<em/sorry you cannot login now/'' type
1150
messages. Information concerning errors in the configuration file,
1151
<tt>/etc/pam.conf</tt>, or due to some system failure encountered by
1152
the module, should be written to <tt/syslog(3)/ with
1153
<em/facility-type/ <tt/LOG_AUTHPRIV/.
1156
With a few exceptions, the level of logging is, at the discretion of
1157
the module developer. Here is the recommended usage of different
1164
As a general rule, errors encountered by a module should be logged at
1165
the <tt/LOG_ERR/ level. However, information regarding an unrecognized
1166
argument, passed to a module from an entry in the
1167
<tt>/etc/pam.conf</tt> file, is <bf/required/ to be logged at the
1171
Debugging information, as activated by the <tt/debug/ argument to the
1172
module in <tt>/etc/pam.conf</tt>, should be logged at the
1173
<tt/LOG_DEBUG/ level.
1176
If a module discovers that its personal configuration file or some
1177
system file it uses for information is corrupted or somehow unusable,
1178
it should indicate this by logging messages at level, <tt/LOG_ALERT/.
1181
Shortages of system resources, such as a failure to manipulate a file
1182
or <tt/malloc()/ failures should be logged at level <tt/LOG_CRIT/.
1185
Authentication failures, associated with an incorrectly typed password
1186
should be logged at level, <tt/LOG_NOTICE/.
1190
<sect1> Modules that require system libraries
1193
Writing a module is much like writing an application. You have to
1194
provide the "conventional hooks" for it to work correctly, like
1195
<tt>pam_sm_authenticate()</tt> etc., which would correspond to the
1196
<tt/main()/ function in a normal function.
1199
Typically, the author may want to link against some standard system
1200
libraries. As when one compiles a normal program, this can be done for
1201
modules too: you simply append the <tt>-l</tt><em>XXX</em> arguments
1202
for the desired libraries when you create the shared module object. To
1203
make sure a module is linked to the <tt>lib<em>whatever</em>.so</tt>
1204
library when it is <tt>dlopen()</tt>ed, try:
1207
% gcc -shared -Xlinker -x -o pam_module.so pam_module.o -lwhatever
1211
<sect1> Added requirements for <em/statically/ loaded modules.
1214
Copyright (C) Michael K. Johnson 1996.
1215
Last modified: AGM 1996/5/31.
1219
Modules may be statically linked into libpam. This should be true of
1220
all the modules distributed with the basic <bf/Linux-PAM/
1221
distribution. To be statically linked, a module needs to export
1222
information about the functions it contains in a manner that does not
1223
clash with other modules.
1225
The extra code necessary to build a static module should be delimited
1226
with <tt/#ifdef PAM_STATIC/ and <tt/#endif/. The static code should do
1229
<item> Define a single structure, <tt/struct pam_module/, called
1230
<tt>_pam_<it>modname</it>_modstruct</tt>, where
1231
<tt><it>modname</it></tt> is the name of the module <bf/as used in the
1232
filesystem/ but without the leading directory name (generally
1233
<tt>/usr/lib/security/</tt> or the suffix (generally <tt/.so/).
1238
As a simple example, consider the following module code which defines
1239
a module that can be compiled to be <em/static/ or <em/dynamic/:
1244
#include <stdio.h> /* for NULL define */
1246
#define PAM_SM_PASSWORD /* the only pam_sm_... function declared */
1247
#include <security/pam_modules.h>
1249
PAM_EXTERN int pam_sm_chauthtok(pam_handle_t *pamh, int flags,
1250
int argc, const char **argv)
1255
#ifdef PAM_STATIC /* for the case that this module is static */
1257
struct pam_module _pam_modname_modstruct = { /* static module data */
1267
#endif /* end PAM_STATIC */
1272
To be linked with <em/libpam/, staticly-linked modules must be built
1273
from within the <tt>Linux-PAM-X.YY/modules/</tt> subdirectory of the
1274
<bf/Linux-PAM/ source directory as part of a normal build of the
1275
<bf/Linux-PAM/ system.
1277
The <em/Makefile/, for the module in question, must execute the
1278
<tt/register_static/ shell script that is located in the
1279
<tt>Linux-PAM-X.YY/modules/</tt> subdirectory. This is to ensure that
1280
the module is properly registered with <em/libpam/.
1282
The <bf/two/ manditory arguments to <tt/register_static/ are the
1283
title, and the pathname of the object file containing the module's
1284
code. The pathname is specified relative to the
1285
<tt>Linux-PAM-X.YY/modules</tt> directory. The pathname may be an
1286
empty string---this is for the case that a single object file needs to
1287
register more than one <tt/struct pam_module/. In such a case, exactly
1288
one call to <tt/register_static/ must indicate the object file.
1291
Here is an example; a line in the <em/Makefile/ might look like this:
1296
(cd ..; ./register_static pam_modname pam_modname/pam_modname.o)
1301
For some further examples, see the <tt>modules</tt> subdirectory of
1302
the current <bf/Linux-PAM/ distribution.
1304
<sect>An example module file
1307
At some point, we may include a fully commented example of a module in
1308
this document. For now, we point the reader to these two locations in
1309
the public CVS repository:
1311
<item> A module that always succeeds: <tt><htmlurl
1312
url="http://cvs.sourceforge.net/cgi-bin/viewcvs.cgi/pam/Linux-PAM/modules/pam_permit/"
1313
name="http://cvs.sourceforge.net/cgi-bin/viewcvs.cgi/pam/Linux-PAM/modules/pam_permit/"
1315
<item> A module that always fails: <tt><htmlurl
1316
url="http://cvs.sourceforge.net/cgi-bin/viewcvs.cgi/pam/Linux-PAM/modules/pam_deny/"
1317
name="http://cvs.sourceforge.net/cgi-bin/viewcvs.cgi/pam/Linux-PAM/modules/pam_deny/"
1325
<tag><tt>/usr/lib/libpam.so.*</tt></tag>
1327
the shared library providing applications with access to
1330
<tag><tt>/etc/pam.conf</tt></tag>
1332
the <bf/Linux-PAM/ configuration file.
1334
<tag><tt>/usr/lib/security/pam_*.so</tt></tag>
1336
the primary location for <bf/Linux-PAM/ dynamically loadable object
1344
<item>The <bf/Linux-PAM/ System Administrators' Guide.
1345
<item>The <bf/Linux-PAM/ Application Writers' Guide.
1347
V. Samar and R. Schemers (SunSoft), ``UNIFIED LOGIN WITH PLUGGABLE
1348
AUTHENTICATION MODULES'', Open Software Foundation Request For
1349
Comments 86.0, October 1995.
1355
I intend to put development comments here... like ``at the moment
1356
this isn't actually supported''. At release time what ever is in
1357
this section will be placed in the Bugs section below! :)
1362
Perhaps we should keep a registry of data-names as used by
1363
<tt/pam_[gs]et_data()/ so there are no unintentional problems due to
1367
<tt/pam_strerror()/ should be internationalized....
1370
There has been some debate about whether <tt/initgroups()/ should be
1371
in an application or in a module. It was settled by Sun who stated
1372
that initgroups is an action of the <em/application/. The modules are
1373
permitted to add additional groups, however.
1376
Refinements/futher suggestions to <tt/syslog(3)/ usage by modules are
1381
<sect>Author/acknowledgments
1384
This document was written by Andrew G. Morgan
1385
(<tt/morgan@kernel.org/) with many contributions from
1386
<!-- insert credits here -->
1388
an sgml list of people to credit for their contributions to Linux-PAM
1389
$Id: pam_modules.sgml,v 1.4 2002/09/15 20:44:05 hartmans Exp $
1396
Derrick J. Brashear,
1415
Luke Kenneth Casson Leighton,
1418
Marek Michalkiewicz,
1428
Savochkin Andrey Vladimirovich,
1437
Thanks are also due to Sun Microsystems, especially to Vipin Samar and
1438
Charlie Lai for their advice. At an early stage in the development of
1439
<bf/Linux-PAM/, Sun graciously made the documentation for their
1440
implementation of PAM available. This act greatly accelerated the
1441
development of <bf/Linux-PAM/.
1443
<sect>Bugs/omissions
1446
Few PAM modules currently exist. Few PAM-aware applications exist.
1447
This document is hopelessly unfinished. Only a partial list of people is
1448
credited for all the good work they have done.
1450
<sect>Copyright information for this document
1453
Copyright (c) Andrew G. Morgan 1996-2002. All rights reserved.
1455
Email: <tt><morgan@kernel.org></tt>
1458
Redistribution and use in source and binary forms, with or without
1459
modification, are permitted provided that the following conditions are
1466
1. Redistributions of source code must retain the above copyright
1467
notice, and the entire permission notice in its entirety,
1468
including the disclaimer of warranties.
1471
2. Redistributions in binary form must reproduce the above copyright
1472
notice, this list of conditions and the following disclaimer in the
1473
documentation and/or other materials provided with the distribution.
1476
3. The name of the author may not be used to endorse or promote
1477
products derived from this software without specific prior
1483
<bf/Alternatively/, this product may be distributed under the terms of
1484
the GNU General Public License (GPL), in which case the provisions of
1485
the GNU GPL are required <bf/instead of/ the above restrictions.
1486
(This clause is necessary due to a potential bad interaction between
1487
the GNU GPL and the restrictions contained in a BSD-style copyright.)
1490
THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED
1491
WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
1492
MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
1493
IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
1494
INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
1495
BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
1496
OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
1497
ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
1498
TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE
1499
USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH
1503
<tt>$Id: pam_modules.sgml,v 1.4 2002/09/15 20:44:05 hartmans Exp $</tt>