[Freeipa-devel] [PATCHES][RFC] Implement special operation to revoer NT hash for a user
Alexander Bokovoy
abokovoy at redhat.com
Fri Jul 27 04:15:46 UTC 2012
On Thu, 12 Jul 2012, Alexander Bokovoy wrote:
>On Thu, 12 Jul 2012, Simo Sorce wrote:
>>On Thu, 2012-07-12 at 10:48 +0300, Alexander Bokovoy wrote:
>>>On Wed, 11 Jul 2012, Simo Sorce wrote:
>>>>From 84ef09a1193ff42fc301fb71354055c5039f51a5 Mon Sep 17 00:00:00 2001
>>>>From: Simo Sorce <ssorce at redhat.com>
>>>>Date: Fri, 6 Jul 2012 16:18:29 -0400
>>>>Subject: [PATCH] Add special modify op to regen ipaNTHash
>>>>
>>>>The NT Hash is the same thing as the RC4-HMAC key, so we add a function to
>>>>extract it from krb5 keys if they are available to avoid forcing a password
>>>>change when configuring trust relationships.
>>>>---
>>>> .../ipa-pwd-extop/ipapwd_prepost.c | 147 +++++++++++++++++++-
>>>> 1 file changed, 144 insertions(+), 3 deletions(-)
>>>>
>>>>diff --git a/daemons/ipa-slapi-plugins/ipa-pwd-extop/ipapwd_prepost.c b/daemons/ipa-slapi-plugins/ipa-pwd-extop/ipapwd_prepost.c
>>>>index deae6477772f82edcc4674a1c9580661c3dae94b..24fa52eb9ac92004576ccdba4f576162c358770d 100644
>>>>--- a/daemons/ipa-slapi-plugins/ipa-pwd-extop/ipapwd_prepost.c
>>>>+++ b/daemons/ipa-slapi-plugins/ipa-pwd-extop/ipapwd_prepost.c
>>>>@@ -41,7 +41,12 @@
>>>> # include <config.h>
>>>> #endif
>>>>
>>>>-#define _XOPEN_SOURCE /* strptime needs this */
>>>>+/* strptime needs _XOPEN_SOURCE and endian.h needs __USE_BSD
>>>>+ * _GNU_SOURCE imply both, and we use it elsewhere, so use this */
>>>>+#ifndef _GNU_SOURCE
>>>>+#define _GNU_SOURCE 1
>>>>+#endif
>>>>+
>>>> #include <stdio.h>
>>>> #include <string.h>
>>>> #include <strings.h>
>>>>@@ -53,6 +58,7 @@
>>>> #include <dirsrv/slapi-plugin.h>
>>>> #include <lber.h>
>>>> #include <time.h>
>>>>+#include <endian.h>
>>>>
>>>> #include "ipapwd.h"
>>>> #include "util.h"
>>>>@@ -379,6 +385,12 @@ done:
>>>> return 0;
>>>> }
>>>>
>>>>+#define NTHASH_REGEN_VAL "MagicRegen"
>>>>+#define NTHASH_REGEN_LEN sizeof(NTHASH_REGEN_VAL)
>>>>+static int ipapwd_regen_nthash(Slapi_PBlock *pb, Slapi_Mods *smods,
>>>>+ char *dn, struct slapi_entry *entry,
>>>>+ struct ipapwd_krbcfg *krbcfg);
>>>>+
>>>> /* PRE MOD Operation:
>>>> * Gets the clean text password (fail the operation if the password came
>>>> * pre-hashed, unless this is a replicated operation).
>>>>@@ -407,6 +419,7 @@ static int ipapwd_pre_mod(Slapi_PBlock *pb)
>>>> int has_krb_keys = 0;
>>>> int has_history = 0;
>>>> int gen_krb_keys = 0;
>>>>+ int is_magic_regen = 0;
>>>> int ret, rc;
>>>>
>>>> LOG_TRACE( "=>\n");
>>>>@@ -447,6 +460,27 @@ static int ipapwd_pre_mod(Slapi_PBlock *pb)
>>>> default:
>>>> break;
>>>> }
>>>>+ } else if (slapi_attr_types_equivalent(lmod->mod_type, "ipaNTHash")) {
>>>>+ /* check op filtering out LDAP_MOD_BVALUES */
>>>>+ switch (lmod->mod_op & 0x0f) {
>>>>+ case LDAP_MOD_REPLACE:
>>>This is still LDAP_MOD_REPLACE, not LDAP_MOD_ADD.
>>
>>This is because I resent the old patch :(
>>
>>Hopefully the correct patch is now attached.
>Yes, now it is updated, thanks.
>
>I'm going to experiment a bit with these patches, adding ipasam
>responder to test them.
Here is ipasam part.
--
/ Alexander Bokovoy
-------------- next part --------------
>From 0cd261dd74154efc9ef6b09ef283cc1fe3448d5e Mon Sep 17 00:00:00 2001
From: Alexander Bokovoy <abokovoy at redhat.com>
Date: Thu, 26 Jul 2012 22:05:25 +0300
Subject: [PATCH 6/6] When ipaNTHash is missing, ask IPA to generate it from
kerberos keys
---
daemons/ipa-sam/ipa_sam.c | 96 +++++++++++++++++++++++++++++++++++++++++++--
1 file changed, 93 insertions(+), 3 deletions(-)
diff --git a/daemons/ipa-sam/ipa_sam.c b/daemons/ipa-sam/ipa_sam.c
index ab4b116c5f2b3b8dae6e8309403afba5fdf86708..aa54429b5bec4b26906b2a34e59ff95299a67f80 100644
--- a/daemons/ipa-sam/ipa_sam.c
+++ b/daemons/ipa-sam/ipa_sam.c
@@ -2400,6 +2400,74 @@ static bool init_sam_from_td(struct samu *user, struct pdb_trusted_domain *td,
return true;
}
+static bool ipasam_nthash_retrieve(struct ldapsam_privates *ldap_state,
+ TALLOC_CTX *mem_ctx,
+ char *entry_dn,
+ DATA_BLOB *nthash)
+{
+ int ret;
+ bool retval;
+ LDAPMessage *result;
+ LDAPMessage *entry = NULL;
+ int count;
+ struct smbldap_state *smbldap_state = ldap_state->smbldap_state;
+ const char *attr_list[] = {
+ LDAP_ATTRIBUTE_NTHASH,
+ NULL
+ };
+
+ ret = smbldap_search(smbldap_state, entry_dn,
+ LDAP_SCOPE_BASE, "", attr_list, 0,
+ &result);
+ if (ret != LDAP_SUCCESS) {
+ DEBUG(1, ("Failed to get NT hash: %s\n",
+ ldap_err2string (ret)));
+ return false;
+ }
+
+ count = ldap_count_entries(smbldap_state->ldap_struct, result);
+
+ if (count != 1) {
+ DEBUG(1, ("Unexpected number of results [%d] for NT hash "
+ "of the single entry search.\n", count));
+ ldap_msgfree(result);
+ return false;
+ }
+
+ entry = ldap_first_entry(smbldap_state->ldap_struct, result);
+ if (entry == NULL) {
+ DEBUG(0, ("Could not get entry\n"));
+ ldap_msgfree(result);
+ return false;
+ }
+
+ retval = smbldap_talloc_single_blob(mem_ctx,
+ smbldap_state->ldap_struct,
+ entry, LDAP_ATTRIBUTE_NTHASH,
+ nthash);
+ ldap_msgfree(result);
+ return retval;
+}
+
+static bool ipasam_nthash_regen(struct ldapsam_privates *ldap_state,
+ TALLOC_CTX *mem_ctx,
+ char * entry_dn)
+{
+ LDAPMod **mods;
+ int ret;
+
+ mods = NULL;
+ smbldap_make_mod(ldap_state->smbldap_state->ldap_struct,
+ NULL, &mods, LDAP_ATTRIBUTE_NTHASH, "MagicRegen");
+
+ talloc_autofree_ldapmod(mem_ctx, mods);
+ ret = smbldap_add(ldap_state->smbldap_state, entry_dn, mods);
+ if (ret != LDAP_SUCCESS) {
+ DEBUG(5, ("ipasam: attempt to regen ipaNTHash failed\n"));
+ }
+ return (ret == LDAP_SUCCESS);
+}
+
static bool init_sam_from_ldap(struct ldapsam_privates *ldap_state,
struct samu * sampass,
LDAPMessage * entry)
@@ -2414,6 +2482,7 @@ static bool init_sam_from_ldap(struct ldapsam_privates *ldap_state,
char *profile_path = NULL;
char *temp = NULL;
bool ret = false;
+ bool retval = false;
DATA_BLOB nthash;
TALLOC_CTX *tmp_ctx = talloc_init("init_sam_from_ldap");
@@ -2504,14 +2573,35 @@ static bool init_sam_from_ldap(struct ldapsam_privates *ldap_state,
pdb_set_acct_ctrl(sampass, ACB_NORMAL, PDB_SET);
- if (!smbldap_talloc_single_blob(tmp_ctx,
+ retval = smbldap_talloc_single_blob(tmp_ctx,
ldap_state->smbldap_state->ldap_struct,
entry, LDAP_ATTRIBUTE_NTHASH,
- &nthash)) {
+ &nthash);
+ if (!retval) {
+ /* NT Hash is not in place. Attempt to retrieve it from
+ * the RC4-HMAC key if that exists in Kerberos credentials.
+ * IPA 389-ds plugin allows to ask for it by setting
+ * ipaNTHash to MagicRegen value.
+ * */
+ temp = smbldap_talloc_dn(tmp_ctx, ldap_state->smbldap_state->ldap_struct, entry);
+ if (temp) {
+ retval = ipasam_nthash_regen(tmp_ctx,
+ ldap_state->smbldap_state->ldap_struct,
+ temp);
+ if (retval) {
+ retval = ipasam_nthash_retrieve(tmp_ctx,
+ ldap_state->smbldap_state->ldap_struct,
+ temp, &nthash);
+ }
+ }
+ }
+
+ if (!retval) {
DEBUG(5, ("Failed to read NT hash form LDAP response.\n"));
}
+
if (nthash.length != NT_HASH_LEN && nthash.length != 0) {
- DEBUG(5, ("NT hash from LDAP has the wrong size.\n"));
+ DEBUG(5, ("NT hash from LDAP has the wrong size. Perhaps password was not re-set?\n"));
} else {
if (!pdb_set_nt_passwd(sampass, nthash.data, PDB_SET)) {
DEBUG(5, ("Failed to set NT hash.\n"));
--
1.7.10.4
More information about the Freeipa-devel
mailing list