Friday, December 9, 2011

OpenLDAP with ppolicy

Overlays are dynamically configurable modules that provide additional functionality to OpenLDAP. The ppolicy overlay provides some useful functionalities for enforcing a password policy for the domain.

Our requirement was the following
  •  Account should be locked out after 5 failed authentication attempts.
  •  Password expiration on 90 days
  •  Minimum password length of 8
All our Ubuntu desktop's were authenticating the OpenLDAP server(example.in) which was setup on a CentOS box. We were able to achieve the 90 day password expiration using the default shadowAccount objectClass as given below.

# user1, People, example.in
dn: uid=user1,ou=People,dc=example,dc=in
uid: user1
cn: user1
objectClass: account
objectClass: posixAccount
objectClass: top
objectClass: shadowAccount
userPassword:: e2NyeXB0fSQxJEMzOxxxxxxxxxx
shadowLastChange: 15299
shadowMax: 90
shadowWarning: 7
loginShell: /bin/bash
uidNumber: 630
gidNumber: 1005
homeDirectory: /data/user1


But we couldn't find any way to implement the password expirartion and password length polcies using the default OpenLDAP configuration. So I started my experiment's with ppolicy overlays. The ppolicy overlays provides enhanced password management capabilities that are applied to non-rootdn bind attempts in OpenLDAP.

Installation
The password policy(ppolicy) and other overlays are included in the package openldap-servers-overlays for Redhat/Centos servers. So we nee first install this package assuming openldap server and dependencies are already installed..
yum install openldap-servers-overlays
The ppolicy module file should get installed at /usr/lib64/openldap/ppolicy.la and schema file at /etc/openldap/schema/ppolicy.schema  on a 64 bit CentOS/Redhat server. The module file should be in /usr/lib/openldap directory on an x86 server.



Server Configuartion
We need to configure the ppolicy overlays now. Add the following lines to /etc/openldap/slapd.conf in the respective sections.

include /etc/openldap/schema/ppolicy.schema

modulepath /usr/lib64/openldap
moduleload ppolicy.la

This is assuming that ppolicy overlay files are in respective locations. The ACL's should be set such that clients bind to OpenLDAP server by self-authentication. We should not allow anonymous or rootdn binds to the server. The default configuration is to allow anonymous binds to server. So I added ACL as given below in the ACL section of slapd.conf.

#ACL
access to attrs=userPassword
by self =xw
by anonymous auth
by * none

access to *
by self write
by * read

Next we need to add default password policy we are going to enforce on the domain. Add the following after the DB section in slapd.conf.

overlay ppolicy
ppolicy_default "cn=default,ou=policies,dc=example,dc=in"
ppolicy_use_lockout


This should complete the configuration of slapd.conf . You should be able to restart the LDAP server without any issues now.


Importing the password policy

Create a LDIF file with following content.

cat password-policy.ldif

dn: ou=policies,dc=example,dc=in
ou: policies
objectClass: top
objectClass: organizationalUnit

# default, policies, example.com
dn: cn=default,ou=policies,dc=example,dc=in
objectClass: top
objectClass: device
objectClass: pwdPolicy
cn: default
pwdAttribute: userPassword
pwdMaxAge: 7776002
pwdExpireWarning: 432000
pwdInHistory: 3
pwdCheckQuality: 1
pwdMinLength: 8
pwdMaxFailure: 5
pwdLockout: TRUE
pwdLockoutDuration: 900
pwdGraceAuthNLimit: 0
pwdFailureCountInterval: 0
pwdMustChange: TRUE
pwdAllowUserChange: TRUE
pwdSafeModify: FALSE


This sets the following policies
  •  password expiration at 90 days
  •  password lockout on 5 failures and lockout duration of 15 mintues
  •  minimum password length of 8
  • 3 earlier password in history

To import the policy run the following command.

ldapadd  -D "cn=Manager,dc=example,dc=in" -W -x  -f password-policy.ldif

This ldapadd command should add to policy on authentication as LDAP administratorWe should be able to see the newly imported policy now when we do a ldapsearch.

 ldapsearch  -x -D "cn=Manager,dc=example,dc=in" -W -b "dc=example,dc=in"

This completes the server configuration. 

Client Side Configuartion
On the LDAP clients in my case Ubuntu desktops we need make the following change in LDAP client configuration file /etc/ldap.conf assuming the client was configured to authenticate to our LDAP server before. Uncomment the pam_lookup_policy line which should be already there in /etc/ldap.conf

pam_lookup_policy yes


Yes !! Now the password policy should be enforced for all non-rootdn authentication attempts !


Reference
http://www.zytrax.com/books/ldap/ch6/ppolicy.html
http://zrmt.com/2007/10/19/howto-ppolicy-openldap
http://linux.die.net/man/5/slapo-ppolicy





7 comments:

  1. after adding
    ldapadd -D "cn=Manager,dc=abc,dc=com" -W -x -f password-policy.ldif

    adding new entry "cn=default,ou=policies,dc=abc,dc=com"
    ldapadd: Invalid syntax (21)
    additional info: objectClass: value #2 invalid per syntax

    ReplyDelete
  2. Thanks for the procedure.

    The only problem is the policies are not applying on the client machine.
    I am using Centos 6.2 on client machine.

    Is there any other setting to be done in Centos client machine.

    ReplyDelete
  3. Policies has been implemented successfully for Unix and Windows machines.

    Thanks for the procedure. Great Work!!!

    ReplyDelete
  4. Sorry, no matter where i put my ppolicy, i always get "Invalid credentials (49)", i create ACL for each of my server, then i put ppolicy just before my DN=users and nothing.
    So, somebody can help my please. THX in advances

    ReplyDelete
  5. Great writeup. However, for some reason my client doesn't seem to be using the overlay properly. The overlay has been added in my ldap configuration and the policy OU is present. But, when I try to do a self change of a password as a user, it doesn't seem to be using any of the password policy attributes. Any thoughts or ideas?

    ReplyDelete
  6. This comment has been removed by the author.

    ReplyDelete
  7. You are a star! This is exactly what I was looking for. Very well explained.

    ReplyDelete