diff options
author | Sumit Bose <sbose@redhat.com> | 2009-12-16 12:53:55 +0100 |
---|---|---|
committer | Stephen Gallagher <sgallagh@redhat.com> | 2009-12-18 09:46:25 -0500 |
commit | 23dc20cd69cfbb2731c36e1610536ba190bbd459 (patch) | |
tree | 106d84e5d8f6a2eef8861a07fa662666ca5ab90f /server/providers/krb5 | |
parent | 66e4134d8be0eb42c645e9730d46bb2c7f561e81 (diff) | |
download | sssd-23dc20cd69cfbb2731c36e1610536ba190bbd459.tar.gz sssd-23dc20cd69cfbb2731c36e1610536ba190bbd459.tar.bz2 sssd-23dc20cd69cfbb2731c36e1610536ba190bbd459.zip |
Handle chauthtok with PAM_PRELIM_CHECK separately
If pam_sm_chauthtok is called with the flag PAM_PRELIM_CHECK set we
generate a separate call to the sssd to validate the old password before
asking for a new password and sending the change password request.
Diffstat (limited to 'server/providers/krb5')
-rw-r--r-- | server/providers/krb5/krb5_auth.c | 14 | ||||
-rw-r--r-- | server/providers/krb5/krb5_child.c | 36 |
2 files changed, 37 insertions, 13 deletions
diff --git a/server/providers/krb5/krb5_auth.c b/server/providers/krb5/krb5_auth.c index 4581278d..73018413 100644 --- a/server/providers/krb5/krb5_auth.c +++ b/server/providers/krb5/krb5_auth.c @@ -398,6 +398,7 @@ static struct krb5_ctx *get_krb5_ctx(struct be_req *be_req) struct krb5_ctx); break; case SSS_PAM_CHAUTHTOK: + case SSS_PAM_CHAUTHTOK_PRELIM: return talloc_get_type(be_req->be_ctx->bet_info[BET_CHPASS].pvt_bet_data, struct krb5_ctx); break; @@ -685,14 +686,16 @@ void krb5_pam_handler(struct be_req *be_req) pd = talloc_get_type(be_req->req_data, struct pam_data); - if (pd->cmd != SSS_PAM_AUTHENTICATE && pd->cmd != SSS_PAM_CHAUTHTOK) { + if (pd->cmd != SSS_PAM_AUTHENTICATE && pd->cmd != SSS_PAM_CHAUTHTOK && + pd->cmd != SSS_PAM_CHAUTHTOK_PRELIM) { DEBUG(4, ("krb5 does not handles pam task %d.\n", pd->cmd)); pam_status = PAM_SUCCESS; dp_err = DP_ERR_OK; goto done; } - if (be_is_offline(be_req->be_ctx) && pd->cmd == SSS_PAM_CHAUTHTOK) { + if (be_is_offline(be_req->be_ctx) && + (pd->cmd == SSS_PAM_CHAUTHTOK || pd->cmd == SSS_PAM_CHAUTHTOK_PRELIM)) { DEBUG(9, ("Password changes are not possible while offline.\n")); pam_status = PAM_AUTHINFO_UNAVAIL; dp_err = DP_ERR_OFFLINE; @@ -958,6 +961,12 @@ static void krb5_child_done(struct tevent_req *req) pd->pam_status = *msg_status; } + if (*msg_status == PAM_SUCCESS && pd->cmd == SSS_PAM_CHAUTHTOK_PRELIM) { + pam_status = PAM_SUCCESS; + dp_err = DP_ERR_OK; + goto done; + } + pref_len = strlen(CCACHE_ENV_NAME)+1; if (*msg_len > pref_len && strncmp((const char *) &buf[p], CCACHE_ENV_NAME"=", pref_len) == 0) { @@ -1047,6 +1056,7 @@ static void krb5_save_ccname_done(struct tevent_req *req) switch(pd->cmd) { case SSS_PAM_AUTHENTICATE: + case SSS_PAM_CHAUTHTOK_PRELIM: password = talloc_size(be_req, pd->authtok_size + 1); if (password != NULL) { memcpy(password, pd->authtok, pd->authtok_size); diff --git a/server/providers/krb5/krb5_child.c b/server/providers/krb5/krb5_child.c index 2f485743..6eb420bc 100644 --- a/server/providers/krb5/krb5_child.c +++ b/server/providers/krb5/krb5_child.c @@ -299,19 +299,24 @@ static struct response *prepare_response_message(struct krb5_req *kr, } if (kerr == 0) { - if (kr->ccname == NULL) { - DEBUG(1, ("Error obtaining ccname.\n")); - return NULL; - } + if(kr->pd->cmd == SSS_PAM_CHAUTHTOK_PRELIM) { + ret = pack_response_packet(resp, PAM_SUCCESS, PAM_USER_INFO, + "success"); + } else { + if (kr->ccname == NULL) { + DEBUG(1, ("Error obtaining ccname.\n")); + return NULL; + } - msg = talloc_asprintf(kr, "%s=%s",CCACHE_ENV_NAME, kr->ccname); - if (msg == NULL) { - DEBUG(1, ("talloc_asprintf failed.\n")); - return NULL; - } + msg = talloc_asprintf(kr, "%s=%s",CCACHE_ENV_NAME, kr->ccname); + if (msg == NULL) { + DEBUG(1, ("talloc_asprintf failed.\n")); + return NULL; + } - ret = pack_response_packet(resp, PAM_SUCCESS, PAM_ENV_ITEM, msg); - talloc_zfree(msg); + ret = pack_response_packet(resp, PAM_SUCCESS, PAM_ENV_ITEM, msg); + talloc_zfree(msg); + } } else { krb5_msg = sss_krb5_get_error_message(krb5_error_ctx, kerr); if (krb5_msg == NULL) { @@ -528,6 +533,14 @@ static errno_t changepw_child(int fd, struct krb5_req *kr) talloc_zfree(pass_str); memset(kr->pd->authtok, 0, kr->pd->authtok_size); + if (kr->pd->cmd == SSS_PAM_CHAUTHTOK_PRELIM) { + DEBUG(9, ("Initial authentication for change password operation " + "successfull.\n")); + krb5_free_cred_contents(kr->ctx, kr->creds); + pam_status = PAM_SUCCESS; + goto sendresponse; + } + newpass_str = talloc_strndup(kr, (const char *) kr->pd->newauthtok, kr->pd->newauthtok_size); if (newpass_str == NULL) { @@ -824,6 +837,7 @@ static int krb5_setup(struct pam_data *pd, const char *user_princ_str, } break; case SSS_PAM_CHAUTHTOK: + case SSS_PAM_CHAUTHTOK_PRELIM: kr->child_req = changepw_child; break; default: |