PAM-PKCS11 User Manual

Release 0.5beta1. 30 Mar 2005


Table of Contents

1. Copyright. Licence
2. Introduction
3. Fundamentals
PKCS #11 Module Requirements
User Matching
4. Installation
5. Configuring pam-pkcs11
Setting up Configuration file
Setting up CRL's and CA's lists
Create map files
6. PAM Configuration
Configuring pam.d files
Sample pam.d entries
7. Using Login auto-detect features
8. Using the Event Manager Tools
Using the Card Event Manager
Structure of configuration file
Using the PKCS#11 Event Manager
Security issues
EXAMPLE: use xscreensaver to lock screen at card removal
9. Using the Login Finder Tool
10. Using the PKCS#11 CertInspect tool
11. What is a cert mapper?
Fundamentals
Implementation of cert mappers in pam-pkcs11
How to use mapfiles
Mappers provided by Pam-pkcs11
Common Name (CN) mapper
Subject mapper
Getpwent() CN to login mapper
LDAP (lightweight directory access protocol) mapper
OpenSC library mapper
OpenSSH library mapper
Email Cert to login mapper
Microsft Universal Principal Name mapper
Kerberos mapper
Unique ID to login mapper
Certificate Digest to login mapper
Null mapper
Adding new mappers
12. Wish list
13. Contact

Abstract

PAM-PKCS#11 is a PAM (Pluggable Authentication Module) libary and related tools to perform login into Linux/UNIX systems by mean of X509 Certificates throught any pkcs#11 compliant library

This manual describes how to compile, install, configure and use pam-pkcs11 PAM module and related tools

Chapter 1. Copyright. Licence

Copyright (C) 2005 Juan Antonio Martinez

Copyright (C) 2003-2004 of Mario Strasser

ScConf library Copyright (C) Antti Tapaninen and Timo Sirainen

Release 0.5beta1. 30 Mar 2005

This library is free software; you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation; either version 2.1 of the License, or (at your option) any later version.

This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details.

You should have received a copy of the GNU Lesser General Public License along with this library; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA

Chapter 2. Introduction

PKCS11_login is a set of libraries and tools to control the process of user login by mean of use any system that support the PKCS11 API

The Linux-PAM login module allows a X.509 certificate based user login. The certificate and its dedicated private key are thereby accessed by means of an appropriate PKCS #11 module. For the verification of the users' certificates, locally stored CA certificates as well as either online or locally accessible CRLs are used.

The Pkcs11 Event Manager is a tool to execute comands at insert or removal of SmartCard from reader. Alternatively, you can use the pcsc-lite's [1] based version

The Pkcs11 Inspect tool allow you to look at the contents of a certificate, in order to help you in the procces of Certificate-to-User mapping configuration

The Pklogin Finder tool can be used to check the pam module without need to do the entire login process, just verifying that login names are properly found and matched

Detailed information about the Linux-PAM system can be found in [2] , [3] and [4] The specification of the Cryptographic Token Interface Standard (PKCS #11) is available at [5]



[1] PCSC-Lite: an Open implementation of PCSC API http://pcsclite.alioth.debian.org/

[2] The Linux-PAM System Administrators' Guide http://www.kernel.org/pub/linux/libs/pam/Linux-PAM-html/pam.html

[4] The Linux-PAM Application Developers' Guide http://www.kernel.org/pub/linux/libs/pam/Linux-PAM-html/pam_appl.html

[5] PKCS #11 - Cryptographic Token Interface Standard http://www.rsasecurity.com/rsalabs/pkcs/pkcs-11/

Chapter 3. Fundamentals

Pam-pcks11 is a PAM ( Pluggable Authentication Module ) pluggin to allow to login into a UNIX/Linux System that supports PAM by mean of use Digital Certificates stored in a SmartCard

To do this, a pkcs11 library is needed to access the Cards. Details on how certificates are stored/retrieved, etc are hidden to pam-pkcs11 and handled by pkcs11 library. This allows independence of the module on an specific card

PKCS #11 Module Requirements

The PKCS #11 modules must full-fit the requirements given by the RSA Asymmetric Client Signing Profile, which has been specified in the PKCS #11 Conformance Profile Specification [6] by RSA Laboratories.

User Matching

To approve the ownership of a certificate, that is, to allow the owner of a certificate to login as a particular user, Pam-pkcs11 uses several modules called mappers that perform cert-to-loggin mapping. See Chapter 11, What is a cert mapper? section

[Note: This is still a work in progress, any suggestions for improvements or alternative matching algorithms are welcome.]



[6] PKCS #11: Conformance Profile Specification http://www.rsasecurity.com/rsalabs/pkcs/pkcs-11/

Chapter 4. Installation

  1. Download source code from official site:/http://www.dit.upm.es/~jantonio/pam-pkcs11/downloads
  2. Unpack source tarball:
    bash# tar -xvzf pkcs11_login-X.Y.tar.gz
    bash# cd pkcs11_login-X.Y
    
  3. If using SVN tree, re-create environment:
    bash# ./bootstrap
    
  4. Execute the "standard" install sequence :-)
    bash# ./configure
    bash# make
    bash# make install
    
  5. Alternatively, on RedHat Linux systems, you can use rpmbuild tools and provided .spec file to create and install RPM packages:
    bash# rpmbuild -ta /path/to/pkcs11_login.X.Y.tar.gz
    bash# rpm -v -i /usr/src/redhat/RPMS/i386/pkcs11_login-X.Y-Z.i386.rpm
    bash# rpm -v -i /usr/src/redhat/RPMS/i386/pkcs11_login-tools-X.Y-Z.i386.rpm
    
  6. Configure package:
    1. Create base configuration directory ( eg. /etc/pkcs11 )
    2. Copy ${base}/etc/pam_pkcs11.conf.example to /etc/pkcs11 and personalize
    3. Create crls and cacerts directories according with configuration file, and fill them with proper data. The tools directory, provides a tool "make_hash_link" that can be used to create hash files on every valid Cert and CRL file.
    4. Choose one o more mappers to install, set up configuration file, and if needed configure mappers. File etc/pam_pkcs11.conf is fully auto-documented, to allow you easy editing
    5. Edit and configure /etc/pam.d/xxx entries. See instructions bellow
    6. Use pkcs11_inspect and pklogin_finder provided tools to see if you can read certificate data and perform correct user mapping
    7. Try to log in. For instance, switch to a tty console
  7. If things go wrong:
    • Ensure that pkcs11 library works properly. You can, for instance, try to use pkcs11 module as engine for OpenSSL or Mozilla/Firefox
    • Re-check configuration
    • If mapping files are used, check it. There are some known problems on some certificates that uses obscure char encodings (non utf-8), that makes CN mappings fail

NOTES

  • To avoid lock the computer, it's recommended try to configure only one non-critical service the first time (eg /etc/pam.d/xscreensaver), and allow normal login on the other services ( /etc/pam.d/gdm )
  • PAM modules used for remote authentication (ie: /etc/pam.d/sshd) cannot be used with pam-pkcs11: !There is no local SmartCard in the server!. To do remote logging, you should use a sort of SingleSignOn service ( kerberos, winbind, and so ) and authenticate against local (client) SmartCard. This is a job in progress

Chapter 5.  Configuring pam-pkcs11

Configuration of pam-pkcs11 involves two steps:

  • Configure pam-pkcs11
  • Configure global PAM options

This chapter explain pam-pkcs11 configuration-related issues. Next one relies on generic PAM options. You should read this manual and study provided configuration sample files before doing any change.

You must know:

  • Which pkcs11 module are you going to use, and its location path
  • Which mapper(s) module(s) do you need, and if needed, how to create and edit related mapping files
  • You'll also need the Certificate Authority files, and if required, the Certificate Revocation Lists ones
  • Of course, the list of authorized users to login, and their corresponding certificates :-). When a remote cert authentication is performed ( eg, via ldap, ADS or NSS), this information must reside, or be accesible in the server

Setting up Configuration file

Configuration file is based on the scconf library

Parameters and data are grouped into blocks. blocks can be nested in a sort of XML tree

pam-pkcs11 config file looks like:

pam-pkcs11 {
	global options
	...
	use_pkcs11_module= pkcs11 module to be used

	pkcs11_module module1 {
		module1 specific options
	}

	pkcs11_module module2 {
		module2 specific options
	}

	[...]

	use_mappers= mapper1, mapper2,... ; 

	mapper mapper1 {
		mapper1 specific options
	}

	mapper mapper2 {
		mapper2 specific options
	}

	[...]
	mapper mapperN {
		mapperN specific options
	}

}

For detailed description see pam_pkcs11.conf.example file

Details on scconf syntax and API are provided in src/scconf/README.scconf file

Setting up CRL's and CA's lists

PAM-pkcs11 needs a list of recognized Certificate authorities, to properly validate certificates. Same applies to Certificate Revocation Lists (if configured to use)

So the process to setup ca and crl entries is:

  1. Create ca_dir and crl_dir directorie entries, according to configuration file
  2. Copy CA Certificates ( either DER or PEM format ) to ca_dir
  3. Create hash links to CA certificates with provided make_hash_link.sh. Note that OpenSSL must be installed
    bash# cd /path/to/ca/dir
    bash# /usr/bin/make_hash_link.sh
    
  4. If CRL are used ( "crl_policy" option in "module" is set to offline or auto ), repeat above process with CRL dir and entries

NOTE: Due to OpenSSL library limitations, CA entries must reside in the local filesystem, and can not be accessed from a remote server. So althought user auth can be done in a remote way, certificate validation must be done locally.

Create map files

If your elected mapper module(s) uses login mapping, you'll need to create and setup mapping files. Some examples are provided in source code.

As a general rule, a mapping file has a newline terminated list of certificate contents -> login entries:

Certificate1 entry data -> login1
Certificate2 data -> login2
Certificate2 data -> login3

Remember that this file is parsed in order, returning on first match

As you can see bellow, mapfile specification doesn't need to be a regular file: you can retrieve data from any legal URL. Anyway, data format must be preserved. See the section called “How to use mapfiles” for additional info

Chapter 6. PAM Configuration

Configuring pam.d files

To make use of the PKCS #11 login module replace the line

auth	requisite	pam_unix2.so	...

with

auth	sufficient	pam_pkcs11.so	...

in the pam.d/serviceXXX configuration files.

Some mappers doesn't map to an existing user. To allow correct login, you may need to install also pam-mkhomedir in session pam stack See http://www.kernel.org/pub/linux/libs/pam for details

The following options are recognised for pam-pkcs11.so:

debug
Enable debugging support.
config_file
To specify up configuration file ( default /etc/pkcs11/pam_pkcs11.conf )

Next options should be taken from configuration file, but is up to the user to specify them from command line. If so, it takes precedence over configuration file

nullok
Allow empty passwords.
use_first_pass
Do not prompt the user for the passwords but take them from the PAM_ items instead.
try_first_pass
Do not prompt the user for the passwords unless PAM_(OLD)AUTHTOK is unset.
use_authtok
Like try_first_pass, but fail if the new PAM_AUTHTOK has not been previously set (intended for stacking password modules only).

Next options are pkcs11 module specific:

pkcs11_module=<files>

Filename of the PKCS #11 module. The default value is /etc/pkcs11/pkcs11_module.so

Note that this option takes precedence over "module" entry in proper pkcs11_module section, but this section is still needed

slot_num=<nr>

Slot-number to use. One for the first, two for the second and so on. The default value is zero which means to use the first slot with an available token.

ca_dir=<path>

Path to the directory where the CA certificates are stored. The directory must contain an openssl hash-link to each certificate. The default value is /etc/pkcs11/cacerts.

Pam-pkcs11 provides an utility: make_hash_link.sh that can be used to create hash links to certificate files. Hashes are used to check certification validity and revocation

crl_dir=<path>
Path to the directory where the CRLs are stored. The directory must contain an openssl hash-link to each CRL. The default value is /etc/pkcs11/crls.
crl_policy={none, online, offline, auto}
Sets the CRL verification policy:
  • none: Performs no verification at all
  • online: Downloads the CRL form the location given by the CRL distribution point extension of the certificate
  • offline: Uses the locally stored CRLs.
  • auto: Is a combination of online and offline: it first tries to download the CRL from a possibly given CRL distribution point and if this fails, uses the local CRLs.
The default setting is none.

Sample pam.d entries

Here comes preferred way to insert pam-pkcs11 into pam stack:

[jantonio@jonsy pkcs11_login-0.4.1]$ cat /etc/pam.d/login
#%PAM-1.0
auth       sufficient    pam_pkcs11.so debug config_file=/etc/pkcs11/pam_pkcs11.conf
auth       required     pam_securetty.so
auth       required     pam_stack.so service=system-auth
auth       required     pam_nologin.so
account    required     pam_stack.so service=system-auth
password   required     pam_stack.so service=system-auth
session    required     pam_stack.so service=system-auth
session    optional     pam_console.so

An alternate way is to explicite options. This is not recommended, but still possible:

#%PAM-1.0
auth	sufficient	pam_pkcs11.so	nullok debug try_first_pass \
	config_file=/etc/pkcs11/pam_pkcs11.conf \
	pkcs11_module=/usr/lib/pkcs11/pkcs11_module.so \
	ca_dir=/etc/cacerts/ crl_dir=/etc/cacerts/ crl_policy=auto
auth       required     pam_securetty.so
auth       required     pam_stack.so service=system-auth
auth       required     pam_nologin.so
account    required     pam_stack.so service=system-auth
password   required     pam_stack.so service=system-auth
session    required     pam_stack.so service=system-auth
session    optional     pam_console.so

In this second example, configuration file is still needed to get mapper module options and flags

Chapter 7. Using Login auto-detect features

Starting at pkcs11_login-0.4.2 a new feature is provided: pam-pkcs11 can deduce user name from certificate, without login prompt

This is done when pam_get_user() call returns null or empty string. In this case, pam-pcks11 use the module mapper "find" feature instead of normal "match".

If the finder list returns ok, evaluated user is set to pam via pam_set_item(PAM_USER) call, and PAM_AUTH_OK is returned

So there are no longer need to enter login name if a certificate is provided and can be mapped to an user

There are to ways for using this feature:

  1. Patch "gdm" and "login" programs to detect card presence and return null as user name, without prompt for an user login. This is a work to be done :-(
  2. Use unpatched versions, and do the following procedures:
    1. When login from console, just enter " " (space) + Enter.
    2. When login from gdm, just key Enter at login prompt.

In both cases the procedure follows as:

  1. If a card is not present, "login" will ask for password then fail; "gdm" will prompt again for user login
  2. If a card is present, pam-pkcs11 will ask for PIN, and then invoke finder in module mapper list. When a user is found, this user become the logged user

This feature can be used with pam-mkhomedir.so PAM Session module. In this case, you can create on-the-fly accounts. This scenario is ideal for centralized auth services ( Winbind, ldap, kerberos, RDBMS auth... )

As example, here comes my tested /etc/pam.d/gdm file:

#%PAM-1.0
auth       sufficient    pam_pkcs11.so debug config_file=/etc/pkcs11/pam_pkcs11.conf
auth       required     pam_env.so
auth       required     pam_stack.so service=system-auth
auth       required     pam_nologin.so
account    required     pam_stack.so service=system-auth
password   required     pam_stack.so service=system-auth
session    required     pam_stack.so service=system-auth
session    optional     pam_mkhomedir.so skel=/etc/skel umask=0022
session    optional     pam_console.so

IMPORTANT NOTES: For pam_set_item(PAM_USER) gets success, application using pam must be enought permissions. If this condition is not met, setting user process will fail and proper log message registered. So this feature is mainly provided for logging processes running as root

Improper mapper chain configurations with unauthorized certificates can lead in create fake accounts in the system if pam_mkhomedir.so module is used. So be really carefull when authenticate users directly from certificates

Chapter 8. Using the Event Manager Tools

PAM-PKCS11 includes several tools: card_eventmgr and pkcs11_eventmgr that can be used to monitorize the status of the card reader and dispatch actions on several events. These programs can be used to several actions, like lock screen on card removal

Note that these programs has no direct interaction with pam-pkcs11 module: they are just a card status monitor. It's up to the sysadmin to define and configure actions to take on events

Using the Card Event Manager

card_eventmgr is a card status monitor based on the PCSC-Lite library

To invoke the program, just type card_eventmgr. Several command lines are recognized:

  • debug to enable debugging. Defaults to unset
  • daemon to run as daemon. If debug is unset, also dettach from tty. Default to unset
  • timeout=<msecs> time in msec between two consecutive status poll. Defaults to 1000 ( 1 second )
  • config_file=<file> configuration file to use. Defaults to /etc/pkcs11/card_eventmgr.conf

Structure of configuration file

Here comes an example of configuration file. Its auto-descriptive:

card_eventmgr {

	# Run in background.
	daemon = false;
	# show debug messages
	debug = false;
	# polling time in mili-seconds
	timeout = 1000;
	#
	# list of events and actions
	#
	# Card inserted
	event card_insert {
		# what to do if an action fail?
		# ignore  : continue to next action
		# return  : end action sequence
		# quit    : end program
		on_error = ignore ;

		# You can enter several, comma-separated action entries
		# they will be executed in turn
		action = "/usr/bin/play /usr/share/sounds/warning.wav",
			"/usr/X11R6/bin/xscreensaver-command -deactivate";
	}

	# Card has been removed
	event card_remove { 
		on_error = ignore;
		action = "/usr/bin/play /usr/share/sounds/error.wav",
			"/usr/X11R6/bin/xscreensaver-command -lock";
	}
}

Using the PKCS#11 Event Manager

Starting pam-pkcs11-0.4.4 a new eventmgr tool is provided: pkcs11_eventmgr. It's very similar to card_eventmgr, with some improvements:

  1. It uses the PKCS#11 library, instead the low-level PCSC-Lite one
  2. Polling time, and expire time are provided in secs, not millisecs
  3. New command line options:
    • [no]debug to enable/disable debugging. Defaults to unset
    • [no]daemon to run as daemon or foreground. If debug is unset, daemon mode also dettaches from tty. Default to "nodaemon"
    • polling_time=<secs> time in secs between two consecutive status poll. Defaults to 1 second
    • expire_time=<secs> time in secs on card removed to trigger "expire_time" event. Default to 0 ( no expire )
    • config_file=<file> configuration file to use. Defaults to /etc/pkcs11/card_eventmgr.conf
    • pkcs11_module=<file> pkcs#11 dll libraryo to use. Defaults to /usr/lib/pkcs11/opensc-pkcs11.so
  4. Expire time on card removal is now supported
  5. Configuration file is sligtly different. See provided example

Here comes pkcs11_cardmgr sample file, with defaults

# Sample pkcs11_eventmgr configuration file
#
pkcs11_eventmgr {

	# Run in background. Implies debug=false
	daemon = true;

	# show debug messages
	debug = false;
	
	# polling time in seconds
	polling_time = 1;

	# expire time in seconds
	# default = 0 ( no expire )
        expire_time = 0;
	
	# pkcs11 module to use
	pkcs11_module = /usr/lib/pkcs11/opensc-pkcs11.so;

	#
	# list of events and actions

	# Card inserted
	event card_insert {
		# what to do if an action fail?
		# ignore  : continue to next action
		# return  : end action sequence
		# quit    : end program
		on_error = ignore ;

		# You can enter several, comma-separated action entries
		# they will be executed in turn
		action = "/usr/bin/play /usr/share/sounds/warning.wav",
			 "/usr/X11R6/bin/xscreensaver-command -deactivate";
	}

	# Card has been removed
	event card_remove { 
		on_error = ignore;
		action = "/usr/bin/play /usr/share/sounds/error.wav",
			 "/usr/X11R6/bin/xscreensaver-command -lock";
	}

	# Too much time card removed
	event expire_time { 
		on_error = ignore;
		action = "/bin/false";
	}
}

As you can see, on each event you can define a list of actions, and what to do if an action fails

Security issues

The best way to start card monitoring is at user login into system. If so, note that all event commands will be executed with user privileges. So is up to the user take care that has permissions to execute desired actions

Special checks should be done when invoke setuid/segid programs: these commands usually ignore the user environment and set up their one. So these applications may not work as expected

Command actions are executed via execve("/bin/sh","-c","provided command",null,environ) in order to avoid risk on system() library call

EXAMPLE: use xscreensaver to lock screen at card removal

You can use provided configuration sample file. Just add to your .xsession or KDE/GNOME Autostart directory an invocation to card_eventmgr in daemon mode

Additionally you can add this entry to /etc/pam.d/xscreensaver configuration

#%PAM-1.0

# Red Hat says this is right for them, as of 7.3:
auth       sufficient    pam_pkcs11.so debug config_file=/etc/pkcs11/pam_pkcs11.conf
auth       required	pam_stack.so service=system-auth

# This is what we were using before:
# auth       required	pam_pwdb.so shadow nullok

In this case, when card is removed the X screen will lock. When card is re-inserted, screen will prompt for the card PIN, check it and if access granted the screen will unlock

NOTES:

  1. Starting pkcs11-login-0.4.4, card_eventmgr tool is no longer supported by pam-pkcs11, and may be removed in newer versions on the package. Users are encouraged to upgrade to pkcs11_eventmgr. This is done to avoid dependencies on low level card management routines
  2. Some PKCS#11 implementations doesn't propperly support C_WaitForSlotEvent() function as defined in pkcs11v2.1 API. So current pkcs11_eventmgr doesn't use it at all, just sleep+rescan tokens. This is a time-consuming behaviour, and may change in future versions of the tool

Chapter 9. Using the Login Finder Tool

PAM-PKCS#11 provides another tool: pklogin-finder, that can be used to find Cert-to-login maps, outside the PAM environment. This tool can be used to create and test map files, or to check environment and configuration files, without need to use PAM related tools

pklogin_finder uses the same structure and configuration than pam-pkcs11 module. It reads certificate, and try all specified mappers to find a user match. When found, login name is displayed on stdout

To invoke, just type from console:

bash$ pklogin_finder [[no]debug] [config_file=<file>]

By default, debug is set to false, and config_file to /etc/pkcs11/pam-pkcs11.conf. All PAM related options (nullok, try_first_pass, and so ) in configuration file are ignored

Return values are:

  • 0 0n sucess, and login name displayed on stdout
  • 1 On no login match found
  • 2 On process error

Chapter 10. Using the PKCS#11 CertInspect tool

Starting at 0.5 version, a new tool pkcs11_inspect is provided

pkcs11_inspect is a pkcs#11 based tool to explore certificate contents. It's similar to pklogin_finder, but no mapping is done at all: just load mappers chains, and in turn, try to get proper data from certificate (ie: cn_mapper looks for CN entries, and so )

When desired info is found, pkcs11_inspect print found data to stdout, without doing any mapping, that is, mapfile entries in configuration file are ignored

The reason to exist for this tool is to ease the making of mapping files:

  • Insert SmartCard
  • Invoke pkcs11_inspect
  • Store result as "left side" of mapfile
  • Edit mapfile and assign contents to a login

Same command line options and configuration file than pklogin_finder applies to pkcs11_inspect command, But note that mapping and ignorecase options will be ignored. See manpage for details

Chapter 11. What is a cert mapper?

Fundamentals

When a X509 Certificate is providen, there are no direct way to map a cert to a login. With a certificate we can check validity and revocation, but user mapping depends entirely on certificate contents

So we need a configurable, stackable, and definable way to specify cert-to-user mapping.

pam-pkcs11 cert mappers provides several functions to:

  1. Search an specific item in certificate
  2. Deduce a login from certificate
  3. Test if a login and a certificate matches

Normal pam-pkcs11 login process involves following procedures:

  1. Enter login
  2. Ask for PIN
  3. Open and validate certificate
  4. Map certificate into an user (*)
  5. Check if login and user matches (**)

An alternate way of working is by mean of not providing user name:

  1. Detect if a card is inserted
  2. Ask for PIN
  3. Open and validate certificate
  4. Map certificate into an user (*)
  5. Open session for deduced login

Last way needs an aditional pam-mkhomedir.so PAM module, that can dinamically create an account

Operations (*) and (**) are the reason for cert-mappers to exist

Implementation of cert mappers in pam-pkcs11

pam-pkcs11 implements cert mapper in form of dinamyc loaded modules. You can add as many modules as desired, and the system will try all of them in turn, until match is done, or end of list get reached

The mapper list is defined in the configuration file:

pam-pkcs11 {
....
    use_mappers = mapper1 [ [[,] mapper2 ] ... ] ;
    ....
    mapper mapper1 {
	debug = false;
	module = /path/to/module.so;
	[ additional mapper dependent options ]
    }
    ....
}

"module" option is mandatory: says pam_pkcs11 where to find dynamic library. Additional entries can be defined but are module dependent

How to use mapfiles

Most of mappers supports the concept of mapfile ,that is, a system to convert a given certificate data item to a user login. The reason are simple:

  • Most certificate contents are no valid for use as login name, and need some way to manage it
  • We can store and manage a list of authorized certificates in a centralized way

The mapfile scheme used in pam-pkcs11 is powerfull: it's not only restricted to files, so we can specify HTTP,LDAP,FTP and so connections, to retrieve mapfile. So this scheme is ideal for centralized accounting systems

The common structure of all mapfiles is:

Certificate 1 entry data -> login1
Cert 2 data -> login2
string from -> string to

That is: a string, the sequence " -> " (space,dash,great,space) and a login

NOTE: It's sintactically correct to specify more than one word in the right-side of a map entry. But be aware that most mappers expect to be returned a single word that provides a user login. Otherwise extrange behaviour may occur. See specific notes on mappers

When a mapper module uses mapfiles, has a structure like:

...
mapper my_mapper {
	...
	mapfile = URL;
}
...

URL is an Universal Resource Locator as defined in corresponding RFC:

  • ftp://user:password@my.host.com/file
  • file:///path/to/local/file
  • https://www.weirdserver.com:8000/
  • ldap://ldap.frontec.se/o=frontec??sub?mail=*sth.frontec.se

Note that depending on compile time options pam-pkcs11 may not support all URL syntax. See Install section and use of --use-curl configure option

Provided source code includes several example mapping files

Mappers provided by Pam-pkcs11

The standard pam-pkcs11 provides following mapper modules:

Common Name (CN) mapper

Assumes CN field on certificate to be the login name.

  • When used as finder, module returns the first CN field found or NULL
  • When used as matcher, it parses certificate and compare all CN fields found against provided login name, returning OK if match found

In either cases, if a mapfile is used, the mapper will try to map CN into a login and use it

Configuration entry is as follow:

  # Common Name (CN) to login mapper
  mapper cn {
        debug = false;
        module = /usr/lib/pam_pkcs11/cn_mapper.so;
	# mapfile = "file:///etc/pkcs11/cn_mapfile;
	ignorecase = false;
	mapfile = "none"
  }

Subject mapper

Extract Certificate Subject and assume it as login.

  • When used as finder, returns mapped login, or assume login=subject if no map found or provided
  • When used as matcher, try to match provided login, with result obtained by previous find operation

In either cases, if a mapfile is used, the mapper will try to map subject into a login and use it

Configuration file is like:

 # Certificate Subject to login mapper
  mapper file {
        debug = false;
        module = /usr/lib/pam_pkcs11/subject_mapper.so;
	ignorecase = true;
	# mapfile = file:///etc/pkcs11/subject_map;
        mapfile = "none";
  }

The mapping file must follow this structure:

....
Certificate Subject -> login
....

Note that some certificates handle extrange char mappings ( non utf-8 ) so you must ensure correct byte-to-byte match. You can use provided pkcs11_inspect tool to get and store correct data from certificate

Getpwent() CN to login mapper

Compare CN against getpwent() library call login or gecos returned values to match user login

  • When used as finder use getpwent() system call to retrieve every users on the system. if pw_name or pw_gecos fields match with CN, pw_name is returned as login name
  • When used as matcher, maps CN to an user with via the finder and matches result with loginname provided by PAM, returning the result (match or no)

Note: newer implementations of getpwent() libraries, use an additional Name Service Swicth (NSS) infrastructure, that allows admins to specify how to obtain requested data. This means you can setup /etc/nsswitch.conf password entries to lookup in to /etc/passwd, or ldap/kerberos/NIS+/YP services

pw_mapper configuration file shows like:
  mapper pw {
        debug = true;
        ignorecase = false;
        module = /usr/lib/pam_pkcs11/pw_mapper.so;
  }

LDAP (lightweight directory access protocol) mapper

Uses an ldap server to retrieve user name. An aditional file tells module the mapping between Cert fields and LDAP entries

This mapper is still under development

OpenSC library mapper

Search certificate in ${HOME}/.eid/autorized_certificates in a similar way as OpenSC does. When used as login finder, returns the user that owns ${HOME} directory where certificate is found

This mapper is still under development

OpenSSH library mapper

Search certificate public key in ${HOME}/.ssh/autorized_keys in a similar way as OpenSSH does. When used as login finder, returns the user that owns ${HOME} directory where key is found

This mapper is still under development

Email Cert to login mapper

Email mapper tries to extract an e-mail from certificate. If found does following procedures:

  • if mapfile option is set and file is provided, the module tries to map email field from the certificate to an user ( or an alternate email ).
  • if mapfile is not set, just use email addres from certificate to perform find/match

Once we have a mapped user, module does:

  • When used as finder, just return email or mapped email/user ( see above )
  • When used as matcher, compare found email/user against provided by pam.

Additionaly you can set ignorecase or ignoredomain flags:

Domain check (if set) is done by testing if provided email domain part ( @ie.this.domain ) matches host domain.

Eg user@my.company.com email in host host.in.my.company.com host matches domain

Configuration file entry looks like:

  mapper mail {
        debug = false;
        module = /usr/lib/pam_pkcs11/mail_mapper.so;
        # MapFile to use
        mapfile = file:///etc/pkcs11/mail_mapping;
        # Some certs store email in uppercase. Take care on this
        ignorecase = true;
        # Also check that host matches mx domain
        ignoredomain = false;
  }

Microsft Universal Principal Name mapper

Try to find and use Microsoft Universal Principal Name (UPN) extension to evaluate login name

Microsoft Universal Principal Name is a ASN1-encoded UTF8 string with the syntax login@ADS_Domain. When an UPN is found, the mapper extract login part as login user. Then, if ignoredomain is unset, try to match domain.

  • When used as finder, returns UPN login as login name (or NULL on fail)
  • When used as matcher compares UPN login against PAM provided login

Configuration file entry looks like:

  mapper ms {
        debug = false;
        module = /usr/lib/pam_pkcs11/ms_mapper.so;
        ignorecase = false;
        ignoredomain = false;
	domainname = "domain.com";
  }

Kerberos mapper

Try to find and use Kerberos Principal Name as login name. if mapfile is specified, maps KPN into a login

NOTES:

  • Kerberos V5 Principal name syntax is assumed: component/component@realm. It's supposed to be stored in ASN1String format in the certificate
  • This mapper does not perform PKINIT kerberos authentication, just retrieve and use KPN to map login name. ( PKINIT auth is still a work in progress)

Configuration entry:

  mapper krb {
        debug = false;
        module = /usr/lib/pam_pkcs11/krb_mapper.so;
	ignorecase = false;
	mapfile = "none";
  }

Unique ID to login mapper

Use Unique ID (UID) field as login name

Similar to CN mapper, but using UID as field to find/match

Configuration entry:

  mapper uid {
        debug = false;
        module = /usr/lib/pam_pkcs11/uid_mapper.so;
	ignorecase = false;
	mapfile = "none";
  }

Certificate Digest to login mapper

Evaluates a certificate digest, and try to map result into a login by using a mapfile

Configuration file should provide the digest algorithm. Depending on OpenSSL configuration all of listed bellow may or not be present in your system

Configuration entry:

  mapper digest {
        debug = false;
        module = /usr/lib/pam_pkcs11/digest_mapper.so;
	# Algorithm used to evaluate certificate digest
        # Select one of:
        # "null","md2","md4","md5","sha","sha1","dss","dss1","ripemd160"
        algorithm = "sha1";
        mapfile = file:///etc/pkcs11/digest_map;
  }

Null mapper

Blind access/deny mapper.

If default_match is set to true:

  • When used as finder allways returns configuration provided default_user ( default: "nobody" )
  • When used as matcher allways returns OK

If default_match is set to false:

  • When used as finder allways returns NULL
  • When used as matcher allways returns FAIL

Configuration entry:

  mapper null {
        debug = false;
        module = /usr/lib/pam_pkcs11/null_mapper.so;
        # select behaviour: allways match, or allways fail
        default_match = false;
	# on match, select returned user
	default_user = nobody;
  }

Adding new mappers

Creating new mappers is easy: just study mapper.h file, provide a file that exports required functions, and modify file src/mappers/Makefile.am

Mapper.h provides default implementation for required exports. They should be overriden by user code, but can be used for testing purposes

You can start by using provided src/mappers/generic_mapper.c skeleton file. Just rename, edit, set Makefile.am properly, and recompile

Chapter 12. Wish list

  1. Make all mappers to use an unified library
  2. Only ask for PIN only when needed ( to extract private key forsignature verification or pkinit challenge process )
  3. Check that certificate is valid for authentication instead of using first found cert
  4. Finish coding all mappers ( openssh, openssl, ldap to be done )
  5. Implement pkinit to talk kerberos server
  6. Debug. I cannot test all cases
  7. Lots of docs and samples needs to be written
  8. Check data types on same certificate contents instead of assume utf8or asn1string
  9. Define and document a mapper API. Create pam_pkcs11-devel package

Chapter 13. Contact

Any comments, suggestions and bug reports are welcome. Please, mention the keywords 'pkcs' and 'pam' in the subject.

Juan Antonio Martinez <jonsito at teleline.es>

Mario Strasser <mast at gmx.net>