Blame SOURCES/0039-sdap-respect-passwordGracelimit.patch

cdf651
From bfafa12ae83bcdec53bb306f68eff9e6acfbb4a6 Mon Sep 17 00:00:00 2001
cdf651
From: =?UTF-8?q?Fabiano=20Fid=C3=AAncio?= <fidencio@redhat.com>
cdf651
Date: Fri, 20 Jul 2018 12:15:18 +0200
cdf651
Subject: [PATCH] sdap: respect passwordGracelimit
cdf651
MIME-Version: 1.0
cdf651
Content-Type: text/plain; charset=UTF-8
cdf651
Content-Transfer-Encoding: 8bit
cdf651
cdf651
Since recent changes in 389-ds two response controls are end when
cdf651
passwordGracelimit is set and about to expire:
cdf651
- [1.3.6.1.4.1.42.2.27.8.5.1] for the GraceLimit itself
cdf651
- [2.16.840.1.113730.3.4.4] for the PasswordExpired
cdf651
cdf651
Whenever the former is returned and the GraceLimit is still valid, we
cdf651
shouldn't report the latter to the users.
cdf651
cdf651
Resolves:
cdf651
https://pagure.io/SSSD/sssd/issue/3597
cdf651
cdf651
Signed-off-by: Fabiano FidĂȘncio <fidencio@redhat.com>
cdf651
cdf651
Reviewed-by: Jakub Hrozek <jhrozek@redhat.com>
cdf651
(cherry picked from commit 954bf82b60b7cfd93b865a6618f155d042b15729)
cdf651
cdf651
DOWNSTREAM:
cdf651
Resolves: rhbz#1522928 - sssd doesn't allow user with expired password
cdf651
to login when PasswordgraceLimit set
cdf651
---
cdf651
 src/providers/ldap/sdap_async_connection.c | 21 ++++++++++++++++++++-
cdf651
 1 file changed, 20 insertions(+), 1 deletion(-)
cdf651
cdf651
diff --git a/src/providers/ldap/sdap_async_connection.c b/src/providers/ldap/sdap_async_connection.c
cdf651
index a8d4262b52c4b2d2810450d68794f00558ea5c2d..8aacd6705a1f82be8c14f97996786ac9b47396d5 100644
cdf651
--- a/src/providers/ldap/sdap_async_connection.c
cdf651
+++ b/src/providers/ldap/sdap_async_connection.c
cdf651
@@ -734,6 +734,7 @@ static void simple_bind_done(struct sdap_op *op,
cdf651
     ber_int_t pp_expire;
cdf651
     LDAPPasswordPolicyError pp_error;
cdf651
     int result = LDAP_OTHER;
cdf651
+    bool on_grace_login_limit = false;
cdf651
 
cdf651
     if (error) {
cdf651
         tevent_req_error(req, error);
cdf651
@@ -772,6 +773,7 @@ static void simple_bind_done(struct sdap_op *op,
cdf651
             DEBUG(SSSDBG_TRACE_INTERNAL,
cdf651
                   "Server returned control [%s].\n",
cdf651
                    response_controls[c]->ldctl_oid);
cdf651
+
cdf651
             if (strcmp(response_controls[c]->ldctl_oid,
cdf651
                        LDAP_CONTROL_PASSWORDPOLICYRESPONSE) == 0) {
cdf651
                 lret = ldap_parse_passwordpolicy_control(state->sh->ldap,
cdf651
@@ -799,13 +801,26 @@ static void simple_bind_done(struct sdap_op *op,
cdf651
                 state->ppolicy->grace = pp_grace;
cdf651
                 state->ppolicy->expire = pp_expire;
cdf651
                 if (result == LDAP_SUCCESS) {
cdf651
-
cdf651
+                    /* We have to set the on_grace_login_limit as when going
cdf651
+                     * through the response controls 389-ds may return both
cdf651
+                     * an warning and an error (and the order is not ensured)
cdf651
+                     * for the GraceLimit:
cdf651
+                     * - [1.3.6.1.4.1.42.2.27.8.5.1] for the GraceLimit itself
cdf651
+                     * - [2.16.840.1.113730.3.4.4] for the PasswordExpired
cdf651
+                     *
cdf651
+                     * So, in order to avoid bulldozing the GraceLimit, let's
cdf651
+                     * set it to true when pp_grace >= 0 and, in the end of
cdf651
+                     * this function, just return EOK when LDAP returns the
cdf651
+                     * PasswordExpired error but the GraceLimit is still valid.
cdf651
+                     */
cdf651
+                    on_grace_login_limit = false;
cdf651
                     if (pp_error == PP_changeAfterReset) {
cdf651
                         DEBUG(SSSDBG_TRACE_LIBS,
cdf651
                               "Password was reset. "
cdf651
                                "User must set a new password.\n");
cdf651
                         ret = ERR_PASSWORD_EXPIRED;
cdf651
                     } else if (pp_grace >= 0) {
cdf651
+                        on_grace_login_limit = true;
cdf651
                         DEBUG(SSSDBG_TRACE_LIBS,
cdf651
                               "Password expired. "
cdf651
                                "[%d] grace logins remaining.\n",
cdf651
@@ -875,6 +890,10 @@ static void simple_bind_done(struct sdap_op *op,
cdf651
         ret = ERR_AUTH_FAILED;
cdf651
     }
cdf651
 
cdf651
+    if (ret == ERR_PASSWORD_EXPIRED && on_grace_login_limit) {
cdf651
+        ret = EOK;
cdf651
+    }
cdf651
+
cdf651
 done:
cdf651
     ldap_controls_free(response_controls);
cdf651
     ldap_memfree(errmsg);
cdf651
-- 
cdf651
2.14.4
cdf651