Hello all,
I am new to this list and I would like to ask you a question regarding OpenLDAP.
The fact is that I have an OpenLDAP server that receive a lot of operations every day. I have different kind of services that make use of LDAP and bind to this server. In a particular case, there are an ou=Users that contain approx. 200 users with their attributes. I am using also a private LDAP schema developed by me in which I have some extra attributes.
Recently we have managed an audit promoted by our government in which a lot of security items had been checked and corrected if had found some issue. One of this security checks was about the management of user passowrds and an other regarding to user accounts. The first one could be satisfied by implementing the ppolicy overlay in LDAP. But in the second one, the audit people imposed us to have a control of which accounts were not being used in the last year, and to delete/backup/etc them if it were the case.
The fact is that I searched for ways of gathering statistics of account usage. The alternatives that I found were:
First, save the statistics in 2 attributes in each user: lastBind, failedBinds.
1. For each service, whenever a bind from a user has done to LDAP, send a ldapmodify operation for this user and if the bind was successful, write in user.lastBind the timestamp. If it was not, increment failedBinds++.
It implies the modification of each service, taking in account that all has to be documented, that in many services the implementation is not trivial, and also taking care of the upgrades of the services. In conclusion, a lot of work and constant modifications and checks.
2. Act on the LDAP server and activate the "overlay accesslog" funcionality. In this case, monitor every bind operation, then create a daemon that reads every X time the LDAP accesslog tree and process it.
For each entry processed: - Delete it from the ldap accesslog tree. - Check if the reqResult was 49 (invalid creds.) or 0 (success). - If it was 49, ldapsearch the reqDN who made the bind request, and read his failedBins attribute. Increment it in one, and send a ldapmodify to the user and with the new value of failedBinds. - If it was 0, ldapmodify the reqDN setting the lastBind as reqEnd.
I programmed it in C++ and ldapc++ library, and it works. But the fact is that I am not convinced of this solution. It saved us from the audit but for the future there are some problems to take into account:
- Deleting the ldap entry every time it's read is bad, because then we cannot use the overlay for delta syncrepl. - Every 10 minutes, ldap deletes the oldest entries, making that in some cases my dameon can fail (treated with an exception, but not cool). - 3000 binds / 10 minutes in normal hours. Up to 40.000 binds in one Monday morning.
My question is obvious. Is there any way other than the daemon, the first option, or suicide, to accomplish the requeriments of the audit? How does a big company to register the last bind of every user account, if this account can use many different and heterogenous services? (VPN, FTP, WEBs, propietary software, Windows samba, Linux login, etc.)
Best regards, sorry for my bad english and for my big post!.
Felip Moll
On 11/25/2011 03:01 PM, Felip Moll wrote:
Hello all,
I am new to this list and I would like to ask you a question regarding OpenLDAP.
The fact is that I have an OpenLDAP server that receive a lot of operations every day. I have different kind of services that make use of LDAP and bind to this server. In a particular case, there are an ou=Users that contain approx. 200 users with their attributes. I am using also a private LDAP schema developed by me in which I have some extra attributes.
Recently we have managed an audit promoted by our government in which a lot of security items had been checked and corrected if had found some issue. One of this security checks was about the management of user passowrds and an other regarding to user accounts. The first one could be satisfied by implementing the ppolicy overlay in LDAP. But in the second one, the audit people imposed us to have a control of which accounts were not being used in the last year, and to delete/backup/etc them if it were the case.
The fact is that I searched for ways of gathering statistics of account usage. The alternatives that I found were:
First, save the statistics in 2 attributes in each user: lastBind, failedBinds.
- For each service, whenever a bind from a user has done to LDAP, send a
ldapmodify operation for this user and if the bind was successful, write in user.lastBind the timestamp. If it was not, increment failedBinds++.
It implies the modification of each service, taking in account that all has to be documented, that in many services the implementation is not trivial, and also taking care of the upgrades of the services. In conclusion, a lot of work and constant modifications and checks.
- Act on the LDAP server and activate the "overlay accesslog"
funcionality. In this case, monitor every bind operation, then create a daemon that reads every X time the LDAP accesslog tree and process it.
For each entry processed:
- Delete it from the ldap accesslog tree.
- Check if the reqResult was 49 (invalid creds.) or 0 (success).
- If it was 49, ldapsearch the reqDN who made the bind request, and read
his failedBins attribute. Increment it in one, and send a ldapmodify to the user and with the new value of failedBinds.
You can use "LDAP Modify-Increment Extension" (RFC4525) instead.
- If it was 0, ldapmodify the reqDN setting the lastBind as reqEnd.
I programmed it in C++ and ldapc++ library, and it works. But the fact is that I am not convinced of this solution. It saved us from the audit but for the future there are some problems to take into account:
- Deleting the ldap entry every time it's read is bad, because then we
cannot use the overlay for delta syncrepl.
You could have multiple accesslogs, or you could only check entries that are newer than the last time the daemon ran (e.g. by filtering for operation type and contextCSN).
p.
Felip Moll wrote:
But in the second one, the audit people imposed us to have a control of which accounts were not being used in the last year, and to delete/backup/etc them if it were the case.
You might wanna use slapo-lastbind in contrib/ for this. This maintains an operational attribute 'authTimestamp' in the user entry which records the last bind time. Unfortunately this seems to only work for LDAP simple binds. With SASL bind the attribute is not updated.
The fact is that I searched for ways of gathering statistics of account usage. The alternatives that I found were:
First, save the statistics in 2 attributes in each user: lastBind, failedBinds.
Attribute 'pwdFailureTime' is already maintained by slapo-ppolicy. The count of attribute values is the number of password failures.
- Act on the LDAP server and activate the "overlay accesslog" funcionality.
In this case, monitor every bind operation, then create a daemon that reads every X time the LDAP accesslog tree and process it.
Yes, this is another option but depending on your deployment the accesslog DB will grow very large very soon if you log all binds.
Ciao, Michael.
Thank you for the tips.
- The LDAP Modify-Increment Extension will be useful to avoid one extra call to ldapsearch.
*"Pierangelo Masarati wrote: You could have multiple accesslogs, or you could only check entries that are newer than the last time the daemon ran (e.g. by filtering for operation type and contextCSN)."*
- Having multiple accesslogs or not delete the entries will cause to have very long results. In the other hand, the daemon also delete the entries every X time, and it's possible to have a deletion of entries before a daemon search.
*"Michael Ströder wrote: You might wanna use slapo-lastbind in contrib/ for this."*
- slapo-lastbind seems interesting, I will take a look to it. I it works I don't care if I don't register every user failedBinds. I'm concerned about SASL, but for now we are not using it.
* "Michael Ströder wrote: Attribute 'pwdFailureTime' is already maintained by slapo-ppolicy. The count of attribute values is the number of password failures."*
- Yes, pwdFailureTime is mantained by slapo-ppolicy but is a global value, not a user value.
Regards, Felip
2011/11/25 Michael Ströder michael@stroeder.com
Felip Moll wrote:
But in the second one, the audit people imposed us to have a control of which accounts were not being used in the last year, and to delete/backup/etc them if it were the case.
You might wanna use slapo-lastbind in contrib/ for this. This maintains an operational attribute 'authTimestamp' in the user entry which records the last bind time. Unfortunately this seems to only work for LDAP simple binds. With SASL bind the attribute is not updated.
The fact is that I searched for ways of gathering statistics of account
usage. The alternatives that I found were:
First, save the statistics in 2 attributes in each user: lastBind, failedBinds.
Attribute 'pwdFailureTime' is already maintained by slapo-ppolicy. The count of attribute values is the number of password failures.
- Act on the LDAP server and activate the "overlay accesslog"
funcionality. In this case, monitor every bind operation, then create a daemon that reads every X time the LDAP accesslog tree and process it.
Yes, this is another option but depending on your deployment the accesslog DB will grow very large very soon if you log all binds.
Ciao, Michael.
You are right, it's an internal attribute while I was searching for a normal one.
Thank you!
2011/11/25 Michael Ströder michael@stroeder.com
Felip Moll wrote:
- Yes, pwdFailureTime is mantained by slapo-ppolicy but is a global
value, not a user value.
No it's maintained in the user's entry recording all failed attempts since the last successful bind. It's reset during next successful bind.
Ciao, Michael.
Hi, Some times ago I found slapo-lastbind useful too, but I faced a (for me) limitation having it not being propagated in a multi-master deploy. Eventually could be the same for you.
However, currently this is a feature request. See ITS#6871 if interested.
Regards Marco
2011/11/25 Felip Moll lipixx@gmail.com
You are right, it's an internal attribute while I was searching for a normal one.
Thank you!
2011/11/25 Michael Ströder michael@stroeder.com
Felip Moll wrote:
- Yes, pwdFailureTime is mantained by slapo-ppolicy but is a global
value, not a user value.
No it's maintained in the user's entry recording all failed attempts since the last successful bind. It's reset during next successful bind.
Ciao, Michael.
openldap-technical@openldap.org