Fixed a number of issues applying password policy against LDAP binds.
See patch for details.
rob
>From 27b19a5fbf7ea999dd9e69732c61ac58668c29b0 Mon Sep 17 00:00:00 2001
From: Rob Crittenden <rcrit...@redhat.com>
Date: Fri, 15 Feb 2013 11:51:59 -0500
Subject: [PATCH] Fix lockout of LDAP bind.
There were several problems:
- A cut-n-paste error where the wrong value was being considered when
an account was administratively unlocked.
- An off-by-one error where LDAP got one extra bind attempt.
- krbPwdPolicyReference wasn't being retrieved as a virtual attribute so
only the global_policy was used.
- The lockout duration wasn't examined in the context of too many failed
logins so was being applied properly.
https://fedorahosted.org/freeipa/ticket/3433
---
.../ipa-slapi-plugins/ipa-lockout/ipa_lockout.c | 41 ++++++++++++++++------
1 file changed, 31 insertions(+), 10 deletions(-)
diff --git a/daemons/ipa-slapi-plugins/ipa-lockout/ipa_lockout.c b/daemons/ipa-slapi-plugins/ipa-lockout/ipa_lockout.c
index fea997d79825e05a6ffe4bf65e22821948794ff3..5aa1f34fa55ee06034fd6f5547d2ea3552842637 100644
--- a/daemons/ipa-slapi-plugins/ipa-lockout/ipa_lockout.c
+++ b/daemons/ipa-slapi-plugins/ipa-lockout/ipa_lockout.c
@@ -588,7 +588,7 @@ done:
static int ipalockout_preop(Slapi_PBlock *pb)
{
char *dn = NULL;
- char *policy_dn = NULL;
+ const char *policy_dn = NULL;
Slapi_Entry *target_entry = NULL;
Slapi_Entry *policy_entry = NULL;
Slapi_DN *sdn = NULL;
@@ -605,6 +605,10 @@ static int ipalockout_preop(Slapi_PBlock *pb)
time_t last_failed = 0;
char *lastfail = NULL;
char *unlock_time = NULL;
+ int type_name_disposition = 0;
+ char *actual_type_name = NULL;
+ int attr_free_flags = 0;
+ Slapi_ValueSet *values = NULL;
LOG_TRACE("--in-->\n");
@@ -656,7 +660,21 @@ static int ipalockout_preop(Slapi_PBlock *pb)
slapi_value_free(&objectclass);
/* Only continue if there is a password policy */
- policy_dn = slapi_entry_attr_get_charptr(target_entry, "krbPwdPolicyReference");
+ ldrc = slapi_vattr_values_get(target_entry, "krbPwdPolicyReference",
+ &values,
+ &type_name_disposition, &actual_type_name,
+ SLAPI_VIRTUALATTRS_REQUEST_POINTERS,
+ &attr_free_flags);
+ if (ldrc == 0) {
+ Slapi_Value *sv = NULL;
+
+ slapi_valueset_first_value(values, &sv);
+
+ if (values != NULL) {
+ policy_dn = slapi_value_get_string(sv);
+ }
+ }
+
if (policy_dn == NULL) {
LOG_TRACE("No kerberos password policy\n");
goto done;
@@ -705,7 +723,7 @@ static int ipalockout_preop(Slapi_PBlock *pb)
time_t unlock;
memset(&tm, 0, sizeof(struct tm));
- res = sscanf(lastfail,
+ res = sscanf(unlock_time,
"%04u%02u%02u%02u%02u%02u",
&tm.tm_year, &tm.tm_mon, &tm.tm_mday,
&tm.tm_hour, &tm.tm_min, &tm.tm_sec);
@@ -730,13 +748,14 @@ static int ipalockout_preop(Slapi_PBlock *pb)
}
lockout_duration = slapi_entry_attr_get_uint(policy_entry, "krbPwdLockoutDuration");
- if (lockout_duration == 0) {
- errstr = "Entry permanently locked.\n";
- ret = LDAP_UNWILLING_TO_PERFORM;
- goto done;
- }
- if (failedcount > max_fail) {
+ if (failedcount >= max_fail) {
+ if (lockout_duration == 0) {
+ errstr = "Entry permanently locked.\n";
+ ret = LDAP_UNWILLING_TO_PERFORM;
+ goto done;
+ }
+
if (time_now < last_failed + lockout_duration) {
/* Too many failures */
LOG_TRACE("Too many failed logins. %lu out of %d\n", failedcount, max_fail);
@@ -748,7 +767,9 @@ static int ipalockout_preop(Slapi_PBlock *pb)
done:
slapi_entry_free(target_entry);
slapi_entry_free(policy_entry);
- if (policy_dn) slapi_ch_free_string(&policy_dn);
+ if (values != NULL) {
+ slapi_vattr_values_free(&values, &actual_type_name, attr_free_flags);
+ }
if (sdn) slapi_sdn_free(&sdn);
LOG("preop returning %d: %s\n", ret, errstr ? errstr : "success\n");
--
1.8.1
_______________________________________________
Freeipa-devel mailing list
Freeipa-devel@redhat.com
https://www.redhat.com/mailman/listinfo/freeipa-devel