When using Kerberos, one way to distribute the user information (such as user ID, groups,and home directory) in your local network is to use LDAP. This requires a strong authentication mechanism that prevents packet spoofing and other attacks. One solution is to use Kerberos for LDAP communication, too.
OpenLDAP implements most authentication flavors through SASL, the simple authentication session layer. SASL is basically a network protocol designed for authentication. The SASL implementation is cyrus-sasl, which supports a number of different authentication flavors. Kerberos authentication is performed through GSSAPI (General Security Services API). By default, the SASL plug-in for GSSAPI is not installed. Install it manually with rpm -ivh cyrus-sasl-gssapi-*.rpm.
To enable Kerberos to bind to the
OpenLDAP server, create a principal
ldap/earth.example.com
and add that to the keytab.
By default, the LDAP server slapd runs as user and group ldap
, while the keytab file is readable by
root
only. Therefore, either
change the LDAP configuration so the server runs as root
or make the keytab file readable by the
group ldap
. The latter is done
automatically by the OpenLDAP start script
(/etc/init.d/ldap
) if the keytab file has been
specified in the OPENLDAP_KRB5_KEYTAB
variable in
/etc/sysconfig/openldap
and the
OPENLDAP_CHOWN_DIRS
variable is set to yes
,
which is the default setting. If OPENLDAP_KRB5_KEYTAB
is left
empty, the default keytab under /etc/krb5.keytab
is
used and you must adjust the privileges yourself as described below.
To run slapd as root
, edit /etc/sysconfig/openldap
.
Disable the OPENLDAP_USER
and
OPENLDAP_GROUP
variables by putting a comment
character in front of them.
To make the keytab file readable by group LDAP, execute
chgrp ldap /etc/krb5.keytab chmod 640 /etc/krb5.keytab
A third, and maybe the best solution, is to tell OpenLDAP to use a special keytab file. To do this, start kadmin, and enter the following command after you have added the principal ldap/earth.example.com:
ktadd -k /etc/openldap/ldap.keytab ldap/earth.example.com@EXAMPLE.COM
Then, on the shell, run:
chown ldap.ldap /etc/openldap/ldap.keytab chmod 600 /etc/openldap/ldap.keytab
To tell OpenLDAP to use a different keytab file, change the
following variable in /etc/sysconfig/openldap
:
OPENLDAP_KRB5_KEYTAB="/etc/openldap/ldap.keytab"
Finally, restart the LDAP server using
rcldap restart
.
You should now be able to use tools, such as ldapsearch, with Kerberos authentication automatically.
ldapsearch -b ou=people,dc=example,dc=com '(uid=newbie)' SASL/GSSAPI authentication started SASL SSF: 56 SASL installing layers [...] # newbie, people, example.com dn: uid=newbie,ou=people,dc=example,dc=com uid: newbie cn: Olaf Kirch [...]
As you can see, ldapsearch prints a message that it started GSSAPI authentication. The next message is very cryptic, but it shows that the security strength factor (SSF for short) is 56 (The value 56 is somewhat arbitrary. Most likely it was chosen because this is the number of bits in a DES encryption key). What this tells you is that GSSAPI authentication was successful and that encryption is being used to provide integrity protection and confidentiality for the LDAP connection.
In Kerberos, authentication is always mutual. This means that not only have you authenticated yourself to the LDAP server, but also the LDAP server authenticated itself to you. In particular, this means communication is with the desired LDAP server, rather than some bogus service set up by an attacker.
Now, allow each user to modify the login shell attribute of their LDAP user
record. Assuming you have a schema where the LDAP entry of user joe
is located at
uid=joe,ou=people,dc=example,dc=com
, set up the
following access controls in /etc/openldap/slapd.conf
:
# This is required for things to work _at all_ access to dn.base="" by * read # Let each user change their login shell access to dn="*,ou=people,dc=example,dc=com" attrs=loginShell by self write # Every user can read everything access to * by users read
The second statement gives authenticated users write access to the
loginShell
attribute of their own LDAP entry. The third
statement gives all authenticated users read access to the entire LDAP
directory.
There is one minor piece of the puzzle missing—how the LDAP
server can find out that the Kerberos user
joe@EXAMPLE.COM
corresponds to the LDAP distinguished
name uid=joe,ou=people,dc=example,dc=com
. This sort of
mapping must be configured manually using the saslExpr
directive. In this example, add the following to
slapd.conf
:
authz-regexp uid=(.*),cn=GSSAPI,cn=auth uid=$1,ou=people,dc=example,dc=com
To understand how this works, you need to know that when SASL authenticates
a user, OpenLDAP forms a distinguished name from
the name given to it by SASL (such as joe
) and the name
of the SASL flavor (GSSAPI
). The result would be
uid=joe,cn=GSSAPI,cn=auth
.
If a authz-regexp
has been configured, it checks the DN
formed from the SASL information using the first argument as a regular
expression. If this regular expression matches, the name is replaced with
the second argument of the authz-regexp
statement. The
placeholder $1
is replaced with the substring matched by
the (.*)
expression.
More complicated match expressions are possible. If you have a more complicated directory structure or a schema in which the username is not part of the DN, you can even use search expressions to map the SASL DN to the user DN.