2 Unix SMB/CIFS implementation.
3 Copyright (C) Andrew Tridgell 1992-2001
4 Copyright (C) Andrew Bartlett 2002
5 Copyright (C) Rafal Szczesniak 2002
6 Copyright (C) Tim Potter 2001
8 This program is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 3 of the License, or
11 (at your option) any later version.
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
18 You should have received a copy of the GNU General Public License
19 along with this program. If not, see <http://www.gnu.org/licenses/>.
22 /* the Samba secrets database stores any generated, private information
23 such as the local SID and machine trust password */
27 #include "../libcli/auth/libcli_auth.h"
29 #include "dbwrap/dbwrap.h"
30 #include "../librpc/ndr/libndr.h"
32 #include "libcli/security/security.h"
34 #include "librpc/gen_ndr/libnet_join.h"
35 #include "librpc/gen_ndr/ndr_secrets.h"
36 #include "lib/crypto/crypto.h"
37 #include "lib/krb5_wrap/krb5_samba.h"
38 #include "lib/util/time_basic.h"
41 #define DBGC_CLASS DBGC_PASSDB
43 static char *domain_info_keystr(const char *domain
);
45 static char *des_salt_key(const char *realm
);
48 * Form a key for fetching the domain sid
50 * @param domain domain name
54 static const char *domain_sid_keystr(const char *domain
)
58 keystr
= talloc_asprintf_strupper_m(talloc_tos(), "%s/%s",
59 SECRETS_DOMAIN_SID
, domain
);
60 SMB_ASSERT(keystr
!= NULL
);
64 static const char *domain_guid_keystr(const char *domain
)
68 keystr
= talloc_asprintf_strupper_m(talloc_tos(), "%s/%s",
69 SECRETS_DOMAIN_GUID
, domain
);
70 SMB_ASSERT(keystr
!= NULL
);
74 static const char *protect_ids_keystr(const char *domain
)
78 keystr
= talloc_asprintf_strupper_m(talloc_tos(), "%s/%s",
79 SECRETS_PROTECT_IDS
, domain
);
80 SMB_ASSERT(keystr
!= NULL
);
84 /* N O T E: never use this outside of passdb modules that store the SID on their own */
85 bool secrets_mark_domain_protected(const char *domain
)
89 ret
= secrets_store(protect_ids_keystr(domain
), "TRUE", 5);
91 DEBUG(0, ("Failed to protect the Domain IDs\n"));
96 bool secrets_clear_domain_protection(const char *domain
)
99 void *protection
= secrets_fetch(protect_ids_keystr(domain
), NULL
);
102 SAFE_FREE(protection
);
103 ret
= secrets_delete_entry(protect_ids_keystr(domain
));
105 DEBUG(0, ("Failed to remove Domain IDs protection\n"));
112 bool secrets_store_domain_sid(const char *domain
, const struct dom_sid
*sid
)
117 protect_ids
= secrets_fetch(protect_ids_keystr(domain
), NULL
);
119 if (strncmp(protect_ids
, "TRUE", 4)) {
120 DEBUG(0, ("Refusing to store a Domain SID, "
121 "it has been marked as protected!\n"));
122 SAFE_FREE(protect_ids
);
126 SAFE_FREE(protect_ids
);
128 ret
= secrets_store(domain_sid_keystr(domain
), sid
, sizeof(struct dom_sid
));
130 /* Force a re-query, in the case where we modified our domain */
132 if (dom_sid_equal(get_global_sam_sid(), sid
) == false) {
133 reset_global_sam_sid();
139 bool secrets_fetch_domain_sid(const char *domain
, struct dom_sid
*sid
)
141 struct dom_sid
*dyn_sid
;
144 dyn_sid
= (struct dom_sid
*)secrets_fetch(domain_sid_keystr(domain
), &size
);
149 if (size
!= sizeof(struct dom_sid
)) {
159 bool secrets_store_domain_guid(const char *domain
, const struct GUID
*guid
)
164 protect_ids
= secrets_fetch(protect_ids_keystr(domain
), NULL
);
166 if (strncmp(protect_ids
, "TRUE", 4)) {
167 DEBUG(0, ("Refusing to store a Domain SID, "
168 "it has been marked as protected!\n"));
169 SAFE_FREE(protect_ids
);
173 SAFE_FREE(protect_ids
);
175 key
= domain_guid_keystr(domain
);
176 return secrets_store(key
, guid
, sizeof(struct GUID
));
179 bool secrets_fetch_domain_guid(const char *domain
, struct GUID
*guid
)
181 struct GUID
*dyn_guid
;
184 struct GUID new_guid
;
186 key
= domain_guid_keystr(domain
);
187 dyn_guid
= (struct GUID
*)secrets_fetch(key
, &size
);
190 if (lp_server_role() == ROLE_DOMAIN_PDC
) {
191 new_guid
= GUID_random();
192 if (!secrets_store_domain_guid(domain
, &new_guid
))
194 dyn_guid
= (struct GUID
*)secrets_fetch(key
, &size
);
196 if (dyn_guid
== NULL
) {
201 if (size
!= sizeof(struct GUID
)) {
202 DEBUG(1,("UUID size %d is wrong!\n", (int)size
));
213 * Form a key for fetching the machine trust account sec channel type
215 * @param domain domain name
219 static const char *machine_sec_channel_type_keystr(const char *domain
)
223 keystr
= talloc_asprintf_strupper_m(talloc_tos(), "%s/%s",
224 SECRETS_MACHINE_SEC_CHANNEL_TYPE
,
226 SMB_ASSERT(keystr
!= NULL
);
231 * Form a key for fetching the machine trust account last change time
233 * @param domain domain name
237 static const char *machine_last_change_time_keystr(const char *domain
)
241 keystr
= talloc_asprintf_strupper_m(talloc_tos(), "%s/%s",
242 SECRETS_MACHINE_LAST_CHANGE_TIME
,
244 SMB_ASSERT(keystr
!= NULL
);
250 * Form a key for fetching the machine previous trust account password
252 * @param domain domain name
256 static const char *machine_prev_password_keystr(const char *domain
)
260 keystr
= talloc_asprintf_strupper_m(talloc_tos(), "%s/%s",
261 SECRETS_MACHINE_PASSWORD_PREV
, domain
);
262 SMB_ASSERT(keystr
!= NULL
);
267 * Form a key for fetching the machine trust account password
269 * @param domain domain name
273 static const char *machine_password_keystr(const char *domain
)
277 keystr
= talloc_asprintf_strupper_m(talloc_tos(), "%s/%s",
278 SECRETS_MACHINE_PASSWORD
, domain
);
279 SMB_ASSERT(keystr
!= NULL
);
284 * Form a key for fetching the machine trust account password
286 * @param domain domain name
288 * @return stored password's key
290 static const char *trust_keystr(const char *domain
)
294 keystr
= talloc_asprintf_strupper_m(talloc_tos(), "%s/%s",
295 SECRETS_MACHINE_ACCT_PASS
, domain
);
296 SMB_ASSERT(keystr
!= NULL
);
300 /************************************************************************
301 Routine to get the default secure channel type for trust accounts
302 ************************************************************************/
304 enum netr_SchannelType
get_default_sec_channel(void)
306 if (lp_server_role() == ROLE_DOMAIN_BDC
||
307 lp_server_role() == ROLE_DOMAIN_PDC
||
308 lp_server_role() == ROLE_ACTIVE_DIRECTORY_DC
) {
311 return SEC_CHAN_WKSTA
;
315 /************************************************************************
316 Routine to get the trust account password for a domain.
317 This only tries to get the legacy hashed version of the password.
318 The user of this function must have locked the trust password file using
319 the above secrets_lock_trust_account_password().
320 ************************************************************************/
322 bool secrets_fetch_trust_account_password_legacy(const char *domain
,
324 time_t *pass_last_set_time
,
325 enum netr_SchannelType
*channel
)
327 struct machine_acct_pass
*pass
;
330 if (!(pass
= (struct machine_acct_pass
*)secrets_fetch(
331 trust_keystr(domain
), &size
))) {
332 DEBUG(5, ("secrets_fetch failed!\n"));
336 if (size
!= sizeof(*pass
)) {
337 DEBUG(0, ("secrets were of incorrect size!\n"));
342 if (pass_last_set_time
) {
343 *pass_last_set_time
= pass
->mod_time
;
345 memcpy(ret_pwd
, pass
->hash
, 16);
348 *channel
= get_default_sec_channel();
355 /************************************************************************
356 Routine to get the trust account password for a domain.
357 The user of this function must have locked the trust password file using
358 the above secrets_lock_trust_account_password().
359 ************************************************************************/
361 bool secrets_fetch_trust_account_password(const char *domain
, uint8_t ret_pwd
[16],
362 time_t *pass_last_set_time
,
363 enum netr_SchannelType
*channel
)
367 plaintext
= secrets_fetch_machine_password(domain
, pass_last_set_time
,
370 DEBUG(4,("Using cleartext machine password\n"));
371 E_md4hash(plaintext
, ret_pwd
);
372 SAFE_FREE(plaintext
);
376 return secrets_fetch_trust_account_password_legacy(domain
, ret_pwd
,
381 /************************************************************************
382 Routine to delete all information related to the domain joined machine.
383 ************************************************************************/
385 bool secrets_delete_machine_password_ex(const char *domain
, const char *realm
)
387 const char *tmpkey
= NULL
;
390 tmpkey
= domain_info_keystr(domain
);
391 ok
= secrets_delete(tmpkey
);
397 tmpkey
= des_salt_key(domain
);
398 ok
= secrets_delete(tmpkey
);
404 tmpkey
= domain_guid_keystr(domain
);
405 ok
= secrets_delete(tmpkey
);
410 tmpkey
= machine_prev_password_keystr(domain
);
411 ok
= secrets_delete(tmpkey
);
416 tmpkey
= machine_password_keystr(domain
);
417 ok
= secrets_delete(tmpkey
);
422 tmpkey
= machine_sec_channel_type_keystr(domain
);
423 ok
= secrets_delete(tmpkey
);
428 tmpkey
= machine_last_change_time_keystr(domain
);
429 ok
= secrets_delete(tmpkey
);
434 tmpkey
= domain_sid_keystr(domain
);
435 ok
= secrets_delete(tmpkey
);
443 /************************************************************************
444 Routine to delete the domain sid
445 ************************************************************************/
447 bool secrets_delete_domain_sid(const char *domain
)
449 return secrets_delete_entry(domain_sid_keystr(domain
));
452 /************************************************************************
453 Set the machine trust account password, the old pw and last change
454 time, domain SID and salting principals based on values passed in
455 (added to supprt the secrets_tdb_sync module on secrets.ldb)
456 ************************************************************************/
458 bool secrets_store_machine_pw_sync(const char *pass
, const char *oldpass
, const char *domain
,
460 const char *salting_principal
, uint32_t supported_enc_types
,
461 const struct dom_sid
*domain_sid
, uint32_t last_change_time
,
462 uint32_t secure_channel_type
,
466 uint8_t last_change_time_store
[4];
467 TALLOC_CTX
*frame
= talloc_stackframe();
468 uint8_t sec_channel_bytes
[4];
471 secrets_delete_machine_password_ex(domain
, realm
);
476 ret
= secrets_store(machine_password_keystr(domain
), pass
, strlen(pass
)+1);
483 ret
= secrets_store(machine_prev_password_keystr(domain
), oldpass
, strlen(oldpass
)+1);
485 ret
= secrets_delete(machine_prev_password_keystr(domain
));
492 if (secure_channel_type
== 0) {
493 /* We delete this and instead have the read code fall back to
494 * a default based on server role, as our caller can't specify
495 * this with any more certainty */
496 ret
= secrets_delete(machine_sec_channel_type_keystr(domain
));
502 SIVAL(&sec_channel_bytes
, 0, secure_channel_type
);
503 ret
= secrets_store(machine_sec_channel_type_keystr(domain
),
504 &sec_channel_bytes
, sizeof(sec_channel_bytes
));
511 SIVAL(&last_change_time_store
, 0, last_change_time
);
512 ret
= secrets_store(machine_last_change_time_keystr(domain
),
513 &last_change_time_store
, sizeof(last_change_time
));
520 ret
= secrets_store_domain_sid(domain
, domain_sid
);
528 char *key
= des_salt_key(realm
);
530 if (salting_principal
!= NULL
) {
531 ret
= secrets_store(key
,
533 strlen(salting_principal
)+1);
535 ret
= secrets_delete(key
);
543 /************************************************************************
544 Return the standard DES salt key
545 ************************************************************************/
547 char* kerberos_standard_des_salt( void )
551 fstr_sprintf( salt
, "host/%s.%s@", lp_netbios_name(), lp_realm() );
552 (void)strlower_m( salt
);
553 fstrcat( salt
, lp_realm() );
555 return SMB_STRDUP( salt
);
558 /************************************************************************
559 ************************************************************************/
561 static char *des_salt_key(const char *realm
)
565 keystr
= talloc_asprintf_strupper_m(talloc_tos(), "%s/DES/%s",
566 SECRETS_SALTING_PRINCIPAL
,
568 SMB_ASSERT(keystr
!= NULL
);
572 /************************************************************************
573 ************************************************************************/
575 bool kerberos_secrets_store_des_salt( const char* salt
)
580 key
= des_salt_key(lp_realm());
582 DEBUG(0,("kerberos_secrets_store_des_salt: failed to generate key!\n"));
587 DEBUG(8,("kerberos_secrets_store_des_salt: deleting salt\n"));
588 secrets_delete_entry( key
);
592 DEBUG(3,("kerberos_secrets_store_des_salt: Storing salt \"%s\"\n", salt
));
594 ret
= secrets_store( key
, salt
, strlen(salt
)+1 );
601 /************************************************************************
602 ************************************************************************/
605 char* kerberos_secrets_fetch_des_salt( void )
609 key
= des_salt_key(lp_realm());
611 DEBUG(0,("kerberos_secrets_fetch_des_salt: failed to generate key!\n"));
615 salt
= (char*)secrets_fetch( key
, NULL
);
622 /************************************************************************
623 Routine to get the salting principal for this service.
624 Caller must free if return is not null.
625 ************************************************************************/
627 char *kerberos_secrets_fetch_salt_princ(void)
630 /* lookup new key first */
632 salt_princ_s
= kerberos_secrets_fetch_des_salt();
633 if (salt_princ_s
== NULL
) {
634 /* fall back to host/machine.realm@REALM */
635 salt_princ_s
= kerberos_standard_des_salt();
641 /************************************************************************
642 Routine to fetch the previous plaintext machine account password for a realm
643 the password is assumed to be a null terminated ascii string.
644 ************************************************************************/
646 char *secrets_fetch_prev_machine_password(const char *domain
)
648 return (char *)secrets_fetch(machine_prev_password_keystr(domain
), NULL
);
651 /************************************************************************
652 Routine to fetch the last change time of the machine account password
654 ************************************************************************/
656 time_t secrets_fetch_pass_last_set_time(const char *domain
)
658 uint32_t *last_set_time
;
659 time_t pass_last_set_time
;
661 last_set_time
= secrets_fetch(machine_last_change_time_keystr(domain
),
664 pass_last_set_time
= IVAL(last_set_time
,0);
665 SAFE_FREE(last_set_time
);
667 pass_last_set_time
= 0;
670 return pass_last_set_time
;
673 /************************************************************************
674 Routine to fetch the plaintext machine account password for a realm
675 the password is assumed to be a null terminated ascii string.
676 ************************************************************************/
678 char *secrets_fetch_machine_password(const char *domain
,
679 time_t *pass_last_set_time
,
680 enum netr_SchannelType
*channel
)
683 ret
= (char *)secrets_fetch(machine_password_keystr(domain
), NULL
);
685 if (pass_last_set_time
) {
686 *pass_last_set_time
= secrets_fetch_pass_last_set_time(domain
);
691 uint32_t *channel_type
;
692 channel_type
= (unsigned int *)secrets_fetch(machine_sec_channel_type_keystr(domain
), &size
);
694 *channel
= IVAL(channel_type
,0);
695 SAFE_FREE(channel_type
);
697 *channel
= get_default_sec_channel();
704 static char *domain_info_keystr(const char *domain
)
708 keystr
= talloc_asprintf_strupper_m(talloc_tos(), "%s/%s",
709 SECRETS_MACHINE_DOMAIN_INFO
,
711 SMB_ASSERT(keystr
!= NULL
);
715 /************************************************************************
716 Routine to get account password to trusted domain
717 ************************************************************************/
719 static NTSTATUS
secrets_fetch_domain_info1_by_key(const char *key
,
721 struct secrets_domain_info1
**_info1
)
723 struct secrets_domain_infoB sdib
= { .version
= 0, };
724 enum ndr_err_code ndr_err
;
725 /* unpacking structures */
728 /* fetching trusted domain password structure */
729 blob
.data
= (uint8_t *)secrets_fetch(key
, &blob
.length
);
730 if (blob
.data
== NULL
) {
731 DBG_NOTICE("secrets_fetch failed!\n");
732 return NT_STATUS_OBJECT_NAME_NOT_FOUND
;
735 /* unpack trusted domain password */
736 ndr_err
= ndr_pull_struct_blob(&blob
, mem_ctx
, &sdib
,
737 (ndr_pull_flags_fn_t
)ndr_pull_secrets_domain_infoB
);
738 SAFE_FREE(blob
.data
);
739 if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err
)) {
740 DBG_ERR("ndr_pull_struct_blob failed - %s!\n",
741 ndr_errstr(ndr_err
));
742 return NT_STATUS_INTERNAL_DB_CORRUPTION
;
745 if (sdib
.version
!= SECRETS_DOMAIN_INFO_VERSION_1
) {
746 DBG_ERR("sdib.version = %u\n", (unsigned)sdib
.version
);
747 return NT_STATUS_INTERNAL_DB_CORRUPTION
;
750 *_info1
= sdib
.info
.info1
;
751 return NT_STATUS_OK
;;
754 static NTSTATUS
secrets_fetch_domain_info(const char *domain
,
756 struct secrets_domain_info1
**pinfo
)
758 char *key
= domain_info_keystr(domain
);
759 return secrets_fetch_domain_info1_by_key(key
, mem_ctx
, pinfo
);
762 void secrets_debug_domain_info(int lvl
, const struct secrets_domain_info1
*info1
,
765 struct secrets_domain_infoB sdib
= {
766 .version
= SECRETS_DOMAIN_INFO_VERSION_1
,
769 sdib
.info
.info1
= discard_const_p(struct secrets_domain_info1
, info1
);
771 ndr_print_debug((ndr_print_fn_t
)ndr_print_secrets_domain_infoB
,
775 char *secrets_domain_info_string(TALLOC_CTX
*mem_ctx
, const struct secrets_domain_info1
*info1
,
776 const char *name
, bool include_secrets
)
778 TALLOC_CTX
*frame
= talloc_stackframe();
779 struct secrets_domain_infoB sdib
= {
780 .version
= SECRETS_DOMAIN_INFO_VERSION_1
,
782 struct ndr_print
*ndr
= NULL
;
785 sdib
.info
.info1
= discard_const_p(struct secrets_domain_info1
, info1
);
787 ndr
= talloc_zero(frame
, struct ndr_print
);
792 ndr
->private_data
= talloc_strdup(ndr
, "");
793 if (ndr
->private_data
== NULL
) {
797 ndr
->print
= ndr_print_string_helper
;
799 ndr
->print_secrets
= include_secrets
;
801 ndr_print_secrets_domain_infoB(ndr
, name
, &sdib
);
802 ret
= talloc_steal(mem_ctx
, (char *)ndr
->private_data
);
807 static NTSTATUS
secrets_store_domain_info1_by_key(const char *key
,
808 const struct secrets_domain_info1
*info1
)
810 struct secrets_domain_infoB sdib
= {
811 .version
= SECRETS_DOMAIN_INFO_VERSION_1
,
813 /* packing structures */
815 enum ndr_err_code ndr_err
;
818 sdib
.info
.info1
= discard_const_p(struct secrets_domain_info1
, info1
);
820 ndr_err
= ndr_push_struct_blob(&blob
, talloc_tos(), &sdib
,
821 (ndr_push_flags_fn_t
)ndr_push_secrets_domain_infoB
);
822 if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err
)) {
823 return ndr_map_error2ntstatus(ndr_err
);
826 ok
= secrets_store(key
, blob
.data
, blob
.length
);
827 data_blob_clear_free(&blob
);
829 return NT_STATUS_INTERNAL_DB_ERROR
;
835 static NTSTATUS
secrets_store_domain_info(const struct secrets_domain_info1
*info
,
838 TALLOC_CTX
*frame
= talloc_stackframe();
839 const char *domain
= info
->domain_info
.name
.string
;
840 const char *realm
= info
->domain_info
.dns_domain
.string
;
841 char *key
= domain_info_keystr(domain
);
842 struct db_context
*db
= NULL
;
843 struct timeval last_change_tv
;
844 const DATA_BLOB
*cleartext_blob
= NULL
;
845 DATA_BLOB pw_blob
= data_blob_null
;
846 DATA_BLOB old_pw_blob
= data_blob_null
;
847 const char *pw
= NULL
;
848 const char *old_pw
= NULL
;
852 int role
= lp_server_role();
854 switch (info
->secure_channel_type
) {
857 if (!upgrade
&& role
>= ROLE_ACTIVE_DIRECTORY_DC
) {
858 DBG_ERR("AD_DC not supported for %s\n",
861 return NT_STATUS_INTERNAL_ERROR
;
866 DBG_ERR("SEC_CHAN_* not supported for %s\n",
869 return NT_STATUS_INTERNAL_ERROR
;
872 db
= secrets_db_ctx();
874 ret
= dbwrap_transaction_start(db
);
876 DBG_ERR("dbwrap_transaction_start() failed for %s\n",
879 return NT_STATUS_INTERNAL_DB_ERROR
;
882 ok
= secrets_clear_domain_protection(domain
);
884 DBG_ERR("secrets_clear_domain_protection(%s) failed\n",
886 dbwrap_transaction_cancel(db
);
888 return NT_STATUS_CANT_ACCESS_DOMAIN_INFO
;
891 ok
= secrets_delete_machine_password_ex(domain
, realm
);
893 DBG_ERR("secrets_delete_machine_password_ex(%s) failed\n",
895 dbwrap_transaction_cancel(db
);
897 return NT_STATUS_CANT_ACCESS_DOMAIN_INFO
;
900 status
= secrets_store_domain_info1_by_key(key
, info
);
901 if (!NT_STATUS_IS_OK(status
)) {
902 DBG_ERR("secrets_store_domain_info1_by_key() failed "
903 "for %s - %s\n", domain
, nt_errstr(status
));
904 dbwrap_transaction_cancel(db
);
910 * We use info->password_last_change instead
911 * of info->password.change_time because
912 * we may want to defer the next change approach
913 * if the server rejected the change the last time,
914 * e.g. due to RefusePasswordChange=1.
916 nttime_to_timeval(&last_change_tv
, info
->password_last_change
);
918 cleartext_blob
= &info
->password
->cleartext_blob
;
919 ok
= convert_string_talloc(frame
, CH_UTF16MUNGED
, CH_UNIX
,
920 cleartext_blob
->data
,
921 cleartext_blob
->length
,
922 (void **)&pw_blob
.data
,
925 status
= NT_STATUS_UNMAPPABLE_CHARACTER
;
926 if (errno
== ENOMEM
) {
927 status
= NT_STATUS_NO_MEMORY
;
929 DBG_ERR("convert_string_talloc(CH_UTF16MUNGED, CH_UNIX) "
930 "failed for pw of %s - %s\n",
931 domain
, nt_errstr(status
));
932 dbwrap_transaction_cancel(db
);
936 pw
= (const char *)pw_blob
.data
;
937 if (info
->old_password
!= NULL
) {
938 cleartext_blob
= &info
->old_password
->cleartext_blob
;
939 ok
= convert_string_talloc(frame
, CH_UTF16MUNGED
, CH_UNIX
,
940 cleartext_blob
->data
,
941 cleartext_blob
->length
,
942 (void **)&old_pw_blob
.data
,
943 &old_pw_blob
.length
);
945 status
= NT_STATUS_UNMAPPABLE_CHARACTER
;
946 if (errno
== ENOMEM
) {
947 status
= NT_STATUS_NO_MEMORY
;
949 DBG_ERR("convert_string_talloc(CH_UTF16MUNGED, CH_UNIX) "
950 "failed for old_pw of %s - %s\n",
951 domain
, nt_errstr(status
));
952 dbwrap_transaction_cancel(db
);
953 data_blob_clear_free(&pw_blob
);
957 old_pw
= (const char *)old_pw_blob
.data
;
960 ok
= secrets_store_machine_pw_sync(pw
, old_pw
,
962 info
->salt_principal
,
963 info
->supported_enc_types
,
964 info
->domain_info
.sid
,
965 last_change_tv
.tv_sec
,
966 info
->secure_channel_type
,
967 false); /* delete_join */
968 data_blob_clear_free(&pw_blob
);
969 data_blob_clear_free(&old_pw_blob
);
971 DBG_ERR("secrets_store_machine_pw_sync(%s) failed\n",
973 dbwrap_transaction_cancel(db
);
975 return NT_STATUS_CANT_ACCESS_DOMAIN_INFO
;
978 if (!GUID_all_zero(&info
->domain_info
.domain_guid
)) {
979 ok
= secrets_store_domain_guid(domain
,
980 &info
->domain_info
.domain_guid
);
982 DBG_ERR("secrets_store_domain_guid(%s) failed\n",
984 dbwrap_transaction_cancel(db
);
986 return NT_STATUS_CANT_ACCESS_DOMAIN_INFO
;
990 ok
= secrets_mark_domain_protected(domain
);
992 DBG_ERR("secrets_mark_domain_protected(%s) failed\n",
994 dbwrap_transaction_cancel(db
);
996 return NT_STATUS_CANT_ACCESS_DOMAIN_INFO
;
999 ret
= dbwrap_transaction_commit(db
);
1001 DBG_ERR("dbwrap_transaction_commit() failed for %s\n",
1004 return NT_STATUS_INTERNAL_DB_ERROR
;
1008 return NT_STATUS_OK
;
1011 static int secrets_domain_info_kerberos_keys(struct secrets_domain_info1_password
*p
,
1012 const char *salt_principal
)
1015 krb5_error_code krb5_ret
;
1016 krb5_context krb5_ctx
= NULL
;
1017 DATA_BLOB cleartext_utf8_b
= data_blob_null
;
1018 krb5_data cleartext_utf8
;
1021 DATA_BLOB aes_256_b
= data_blob_null
;
1022 DATA_BLOB aes_128_b
= data_blob_null
;
1023 DATA_BLOB des_md5_b
= data_blob_null
;
1025 #endif /* HAVE_ADS */
1026 DATA_BLOB arc4_b
= data_blob_null
;
1027 const uint16_t max_keys
= 4;
1028 struct secrets_domain_info1_kerberos_key
*keys
= NULL
;
1030 char *salt_data
= NULL
;
1034 * ENCTYPE_AES256_CTS_HMAC_SHA1_96
1035 * ENCTYPE_AES128_CTS_HMAC_SHA1_96
1036 * ENCTYPE_ARCFOUR_HMAC
1037 * ENCTYPE_DES_CBC_MD5
1039 * We don't include ENCTYPE_DES_CBC_CRC
1040 * as W2008R2 also doesn't store it anymore.
1042 * Note we store all enctypes we support,
1043 * including the weak encryption types,
1044 * but that's no problem as we also
1045 * store the cleartext password anyway.
1047 * Which values are then used to construct
1048 * a keytab is configured at runtime and the
1049 * configuration of msDS-SupportedEncryptionTypes.
1051 * If we don't have kerberos support or no
1052 * salt, we only generate an entry for arcfour-hmac-md5.
1054 keys
= talloc_zero_array(p
,
1055 struct secrets_domain_info1_kerberos_key
,
1061 arc4_b
= data_blob_talloc(keys
,
1063 sizeof(p
->nt_hash
.hash
));
1064 if (arc4_b
.data
== NULL
) {
1065 DBG_ERR("data_blob_talloc failed for arcfour-hmac-md5.\n");
1071 if (salt_principal
== NULL
) {
1075 initialize_krb5_error_table();
1076 krb5_ret
= krb5_init_context(&krb5_ctx
);
1077 if (krb5_ret
!= 0) {
1082 krb5_ret
= smb_krb5_salt_principal2data(krb5_ctx
, salt_principal
,
1084 if (krb5_ret
!= 0) {
1085 DBG_ERR("smb_krb5_salt_principal2data(%s) failed: %s\n",
1087 smb_get_krb5_error_message(krb5_ctx
, krb5_ret
, keys
));
1088 krb5_free_context(krb5_ctx
);
1093 salt
= (krb5_data
) {
1094 .data
= discard_const(salt_data
),
1095 .length
= strlen(salt_data
),
1098 ok
= convert_string_talloc(keys
, CH_UTF16MUNGED
, CH_UTF8
,
1099 p
->cleartext_blob
.data
,
1100 p
->cleartext_blob
.length
,
1101 (void **)&cleartext_utf8_b
.data
,
1102 &cleartext_utf8_b
.length
);
1109 krb5_free_context(krb5_ctx
);
1113 cleartext_utf8
.data
= (void *)cleartext_utf8_b
.data
;
1114 cleartext_utf8
.length
= cleartext_utf8_b
.length
;
1116 krb5_ret
= smb_krb5_create_key_from_string(krb5_ctx
,
1120 ENCTYPE_AES256_CTS_HMAC_SHA1_96
,
1122 if (krb5_ret
!= 0) {
1123 DBG_ERR("generation of a aes256-cts-hmac-sha1-96 key failed: %s\n",
1124 smb_get_krb5_error_message(krb5_ctx
, krb5_ret
, keys
));
1125 krb5_free_context(krb5_ctx
);
1127 TALLOC_FREE(salt_data
);
1130 aes_256_b
= data_blob_talloc(keys
,
1131 KRB5_KEY_DATA(&key
),
1132 KRB5_KEY_LENGTH(&key
));
1133 krb5_free_keyblock_contents(krb5_ctx
, &key
);
1134 if (aes_256_b
.data
== NULL
) {
1135 DBG_ERR("data_blob_talloc failed for aes-256.\n");
1136 krb5_free_context(krb5_ctx
);
1138 TALLOC_FREE(salt_data
);
1142 krb5_ret
= smb_krb5_create_key_from_string(krb5_ctx
,
1146 ENCTYPE_AES128_CTS_HMAC_SHA1_96
,
1148 if (krb5_ret
!= 0) {
1149 DBG_ERR("generation of a aes128-cts-hmac-sha1-96 key failed: %s\n",
1150 smb_get_krb5_error_message(krb5_ctx
, krb5_ret
, keys
));
1151 krb5_free_context(krb5_ctx
);
1153 TALLOC_FREE(salt_data
);
1156 aes_128_b
= data_blob_talloc(keys
,
1157 KRB5_KEY_DATA(&key
),
1158 KRB5_KEY_LENGTH(&key
));
1159 krb5_free_keyblock_contents(krb5_ctx
, &key
);
1160 if (aes_128_b
.data
== NULL
) {
1161 DBG_ERR("data_blob_talloc failed for aes-128.\n");
1162 krb5_free_context(krb5_ctx
);
1164 TALLOC_FREE(salt_data
);
1168 krb5_ret
= smb_krb5_create_key_from_string(krb5_ctx
,
1172 ENCTYPE_DES_CBC_MD5
,
1174 if (krb5_ret
!= 0) {
1175 DBG_ERR("generation of a des-cbc-md5 key failed: %s\n",
1176 smb_get_krb5_error_message(krb5_ctx
, krb5_ret
, keys
));
1177 krb5_free_context(krb5_ctx
);
1179 TALLOC_FREE(salt_data
);
1182 des_md5_b
= data_blob_talloc(keys
,
1183 KRB5_KEY_DATA(&key
),
1184 KRB5_KEY_LENGTH(&key
));
1185 krb5_free_keyblock_contents(krb5_ctx
, &key
);
1186 if (des_md5_b
.data
== NULL
) {
1187 DBG_ERR("data_blob_talloc failed for des-cbc-md5.\n");
1188 krb5_free_context(krb5_ctx
);
1190 TALLOC_FREE(salt_data
);
1194 krb5_free_context(krb5_ctx
);
1197 if (aes_256_b
.length
!= 0) {
1198 keys
[idx
].keytype
= ENCTYPE_AES256_CTS_HMAC_SHA1_96
;
1199 keys
[idx
].iteration_count
= 4096;
1200 keys
[idx
].value
= aes_256_b
;
1204 if (aes_128_b
.length
!= 0) {
1205 keys
[idx
].keytype
= ENCTYPE_AES128_CTS_HMAC_SHA1_96
;
1206 keys
[idx
].iteration_count
= 4096;
1207 keys
[idx
].value
= aes_128_b
;
1211 #endif /* HAVE_ADS */
1213 keys
[idx
].keytype
= ENCTYPE_ARCFOUR_HMAC
;
1214 keys
[idx
].iteration_count
= 4096;
1215 keys
[idx
].value
= arc4_b
;
1219 if (des_md5_b
.length
!= 0) {
1220 keys
[idx
].keytype
= ENCTYPE_DES_CBC_MD5
;
1221 keys
[idx
].iteration_count
= 4096;
1222 keys
[idx
].value
= des_md5_b
;
1225 #endif /* HAVE_ADS */
1227 p
->salt_data
= salt_data
;
1228 p
->default_iteration_count
= 4096;
1234 static NTSTATUS
secrets_domain_info_password_create(TALLOC_CTX
*mem_ctx
,
1235 const char *cleartext_unix
,
1236 const char *salt_principal
,
1238 const char *change_server
,
1239 struct secrets_domain_info1_password
**_p
)
1241 struct secrets_domain_info1_password
*p
= NULL
;
1246 if (change_server
== NULL
) {
1247 return NT_STATUS_INVALID_PARAMETER_MIX
;
1250 p
= talloc_zero(mem_ctx
, struct secrets_domain_info1_password
);
1252 return NT_STATUS_NO_MEMORY
;
1254 p
->change_time
= change_time
;
1255 p
->change_server
= talloc_strdup(p
, change_server
);
1256 if (p
->change_server
== NULL
) {
1258 return NT_STATUS_NO_MEMORY
;
1260 len
= strlen(cleartext_unix
);
1261 ok
= convert_string_talloc(p
, CH_UNIX
, CH_UTF16
,
1262 cleartext_unix
, len
,
1263 (void **)&p
->cleartext_blob
.data
,
1264 &p
->cleartext_blob
.length
);
1266 NTSTATUS status
= NT_STATUS_UNMAPPABLE_CHARACTER
;
1267 if (errno
== ENOMEM
) {
1268 status
= NT_STATUS_NO_MEMORY
;
1273 mdfour(p
->nt_hash
.hash
,
1274 p
->cleartext_blob
.data
,
1275 p
->cleartext_blob
.length
);
1277 ret
= secrets_domain_info_kerberos_keys(p
, salt_principal
);
1279 NTSTATUS status
= krb5_to_nt_status(ret
);
1285 return NT_STATUS_OK
;
1288 NTSTATUS
secrets_fetch_or_upgrade_domain_info(const char *domain
,
1289 TALLOC_CTX
*mem_ctx
,
1290 struct secrets_domain_info1
**pinfo
)
1292 TALLOC_CTX
*frame
= NULL
;
1293 struct secrets_domain_info1
*old
= NULL
;
1294 struct secrets_domain_info1
*info
= NULL
;
1295 const char *dns_domain
= NULL
;
1296 const char *server
= NULL
;
1297 struct db_context
*db
= NULL
;
1298 time_t last_set_time
;
1300 enum netr_SchannelType channel
;
1302 char *old_pw
= NULL
;
1303 struct dom_sid domain_sid
;
1304 struct GUID domain_guid
;
1309 ok
= strequal(domain
, lp_workgroup());
1311 dns_domain
= lp_dnsdomain();
1313 if (dns_domain
!= NULL
&& dns_domain
[0] == '\0') {
1318 last_set_time
= secrets_fetch_pass_last_set_time(domain
);
1319 if (last_set_time
== 0) {
1320 return NT_STATUS_OK
;
1322 unix_to_nt_time(&last_set_nt
, last_set_time
);
1324 frame
= talloc_stackframe();
1326 status
= secrets_fetch_domain_info(domain
, frame
, &old
);
1327 if (NT_STATUS_IS_OK(status
)) {
1328 if (old
->password_last_change
>= last_set_nt
) {
1329 *pinfo
= talloc_move(mem_ctx
, &old
);
1331 return NT_STATUS_OK
;
1336 info
= talloc_zero(frame
, struct secrets_domain_info1
);
1338 DBG_ERR("talloc_zero failed\n");
1340 return NT_STATUS_NO_MEMORY
;
1343 db
= secrets_db_ctx();
1345 ret
= dbwrap_transaction_start(db
);
1347 DBG_ERR("dbwrap_transaction_start() failed for %s\n",
1350 return NT_STATUS_INTERNAL_DB_ERROR
;
1353 pw
= secrets_fetch_machine_password(domain
,
1357 DBG_ERR("secrets_fetch_machine_password(%s) failed\n",
1359 dbwrap_transaction_cancel(db
);
1361 return NT_STATUS_CANT_ACCESS_DOMAIN_INFO
;
1363 unix_to_nt_time(&last_set_nt
, last_set_time
);
1365 old_pw
= secrets_fetch_prev_machine_password(domain
);
1367 ok
= secrets_fetch_domain_sid(domain
, &domain_sid
);
1369 DBG_ERR("secrets_fetch_domain_sid(%s) failed\n",
1371 dbwrap_transaction_cancel(db
);
1375 return NT_STATUS_CANT_ACCESS_DOMAIN_INFO
;
1378 ok
= secrets_fetch_domain_guid(domain
, &domain_guid
);
1380 domain_guid
= GUID_zero();
1383 info
->computer_name
= lp_netbios_name();
1384 info
->account_name
= talloc_asprintf(frame
, "%s$", info
->computer_name
);
1385 if (info
->account_name
== NULL
) {
1386 DBG_ERR("talloc_asprintf(%s$) failed\n", info
->computer_name
);
1387 dbwrap_transaction_cancel(db
);
1391 return NT_STATUS_NO_MEMORY
;
1393 info
->secure_channel_type
= channel
;
1395 info
->domain_info
.name
.string
= domain
;
1396 info
->domain_info
.dns_domain
.string
= dns_domain
;
1397 info
->domain_info
.dns_forest
.string
= dns_domain
;
1398 info
->domain_info
.domain_guid
= domain_guid
;
1399 info
->domain_info
.sid
= &domain_sid
;
1401 info
->trust_flags
= NETR_TRUST_FLAG_PRIMARY
;
1402 info
->trust_flags
|= NETR_TRUST_FLAG_OUTBOUND
;
1404 if (dns_domain
!= NULL
) {
1406 * We just assume all AD domains are
1407 * NETR_TRUST_FLAG_NATIVE these days.
1409 * This isn't used anyway for now.
1411 info
->trust_flags
|= NETR_TRUST_FLAG_NATIVE
;
1413 info
->trust_type
= LSA_TRUST_TYPE_UPLEVEL
;
1415 server
= info
->domain_info
.dns_domain
.string
;
1417 info
->trust_type
= LSA_TRUST_TYPE_DOWNLEVEL
;
1419 server
= talloc_asprintf(info
,
1423 if (server
== NULL
) {
1424 DBG_ERR("talloc_asprintf(%s#%02X) failed\n",
1425 domain
, NBT_NAME_PDC
);
1426 dbwrap_transaction_cancel(db
);
1430 return NT_STATUS_NO_MEMORY
;
1433 info
->trust_attributes
= LSA_TRUST_ATTRIBUTE_TREAT_AS_EXTERNAL
;
1435 info
->join_time
= 0;
1438 * We don't have enough information about the configured
1441 info
->supported_enc_types
= 0;
1442 info
->salt_principal
= NULL
;
1443 if (info
->trust_type
== LSA_TRUST_TYPE_UPLEVEL
) {
1446 p
= kerberos_secrets_fetch_salt_princ();
1448 dbwrap_transaction_cancel(db
);
1452 return NT_STATUS_INTERNAL_ERROR
;
1454 info
->salt_principal
= talloc_strdup(info
, p
);
1456 if (info
->salt_principal
== NULL
) {
1457 dbwrap_transaction_cancel(db
);
1461 return NT_STATUS_NO_MEMORY
;
1465 info
->password_last_change
= last_set_nt
;
1466 info
->password_changes
= 1;
1467 info
->next_change
= NULL
;
1469 status
= secrets_domain_info_password_create(info
,
1471 info
->salt_principal
,
1472 last_set_nt
, server
,
1475 if (!NT_STATUS_IS_OK(status
)) {
1476 DBG_ERR("secrets_domain_info_password_create(pw) failed "
1477 "for %s - %s\n", domain
, nt_errstr(status
));
1478 dbwrap_transaction_cancel(db
);
1485 * After a join we don't have old passwords.
1487 if (old_pw
!= NULL
) {
1488 status
= secrets_domain_info_password_create(info
,
1490 info
->salt_principal
,
1492 &info
->old_password
);
1494 if (!NT_STATUS_IS_OK(status
)) {
1495 DBG_ERR("secrets_domain_info_password_create(old) failed "
1496 "for %s - %s\n", domain
, nt_errstr(status
));
1497 dbwrap_transaction_cancel(db
);
1501 info
->password_changes
+= 1;
1503 info
->old_password
= NULL
;
1505 info
->older_password
= NULL
;
1507 secrets_debug_domain_info(DBGLVL_INFO
, info
, "upgrade");
1509 status
= secrets_store_domain_info(info
, true /* upgrade */);
1510 if (!NT_STATUS_IS_OK(status
)) {
1511 DBG_ERR("secrets_store_domain_info() failed "
1512 "for %s - %s\n", domain
, nt_errstr(status
));
1513 dbwrap_transaction_cancel(db
);
1519 * We now reparse it.
1521 status
= secrets_fetch_domain_info(domain
, frame
, &info
);
1522 if (!NT_STATUS_IS_OK(status
)) {
1523 DBG_ERR("secrets_fetch_domain_info() failed "
1524 "for %s - %s\n", domain
, nt_errstr(status
));
1525 dbwrap_transaction_cancel(db
);
1530 ret
= dbwrap_transaction_commit(db
);
1532 DBG_ERR("dbwrap_transaction_commit() failed for %s\n",
1534 dbwrap_transaction_cancel(db
);
1536 return NT_STATUS_INTERNAL_DB_ERROR
;
1539 *pinfo
= talloc_move(mem_ctx
, &info
);
1541 return NT_STATUS_OK
;
1544 NTSTATUS
secrets_store_JoinCtx(const struct libnet_JoinCtx
*r
)
1546 TALLOC_CTX
*frame
= talloc_stackframe();
1547 struct secrets_domain_info1
*old
= NULL
;
1548 struct secrets_domain_info1
*info
= NULL
;
1549 struct db_context
*db
= NULL
;
1550 struct timeval tv
= timeval_current();
1551 NTTIME now
= timeval_to_nttime(&tv
);
1552 const char *domain
= r
->out
.netbios_domain_name
;
1556 info
= talloc_zero(frame
, struct secrets_domain_info1
);
1558 DBG_ERR("talloc_zero failed\n");
1560 return NT_STATUS_NO_MEMORY
;
1563 info
->computer_name
= r
->in
.machine_name
;
1564 info
->account_name
= r
->out
.account_name
;
1565 info
->secure_channel_type
= r
->in
.secure_channel_type
;
1567 info
->domain_info
.name
.string
=
1568 r
->out
.netbios_domain_name
;
1569 info
->domain_info
.dns_domain
.string
=
1570 r
->out
.dns_domain_name
;
1571 info
->domain_info
.dns_forest
.string
=
1573 info
->domain_info
.domain_guid
= r
->out
.domain_guid
;
1574 info
->domain_info
.sid
= r
->out
.domain_sid
;
1576 info
->trust_flags
= NETR_TRUST_FLAG_PRIMARY
;
1577 info
->trust_flags
|= NETR_TRUST_FLAG_OUTBOUND
;
1578 if (r
->out
.domain_is_ad
) {
1580 * We just assume all AD domains are
1581 * NETR_TRUST_FLAG_NATIVE these days.
1583 * This isn't used anyway for now.
1585 info
->trust_flags
|= NETR_TRUST_FLAG_NATIVE
;
1587 info
->trust_type
= LSA_TRUST_TYPE_UPLEVEL
;
1589 info
->trust_type
= LSA_TRUST_TYPE_DOWNLEVEL
;
1591 info
->trust_attributes
= LSA_TRUST_ATTRIBUTE_TREAT_AS_EXTERNAL
;
1593 info
->join_time
= now
;
1595 info
->supported_enc_types
= r
->out
.set_encryption_types
;
1596 info
->salt_principal
= r
->out
.krb5_salt
;
1598 if (info
->salt_principal
== NULL
&& r
->out
.domain_is_ad
) {
1601 ret
= smb_krb5_salt_principal(info
->domain_info
.dns_domain
.string
,
1603 NULL
/* userPrincipalName */,
1604 true /* is_computer */,
1607 status
= krb5_to_nt_status(ret
);
1608 DBG_ERR("smb_krb5_salt_principal() failed "
1609 "for %s - %s\n", domain
, nt_errstr(status
));
1613 info
->salt_principal
= p
;
1616 info
->password_last_change
= now
;
1617 info
->password_changes
= 1;
1618 info
->next_change
= NULL
;
1620 status
= secrets_domain_info_password_create(info
,
1621 r
->in
.machine_password
,
1622 info
->salt_principal
,
1625 if (!NT_STATUS_IS_OK(status
)) {
1626 DBG_ERR("secrets_domain_info_password_create(pw) failed "
1627 "for %s - %s\n", domain
, nt_errstr(status
));
1632 db
= secrets_db_ctx();
1634 ret
= dbwrap_transaction_start(db
);
1636 DBG_ERR("dbwrap_transaction_start() failed for %s\n",
1639 return NT_STATUS_INTERNAL_DB_ERROR
;
1642 status
= secrets_fetch_or_upgrade_domain_info(domain
, frame
, &old
);
1643 if (NT_STATUS_EQUAL(status
, NT_STATUS_CANT_ACCESS_DOMAIN_INFO
)) {
1644 DBG_DEBUG("no old join for domain(%s) available\n",
1647 } else if (!NT_STATUS_IS_OK(status
)) {
1648 DBG_ERR("secrets_fetch_or_upgrade_domain_info(%s) failed\n",
1650 dbwrap_transaction_cancel(db
);
1656 * We reuse values from an old join, so that
1657 * we still accept already granted kerberos tickets.
1660 info
->old_password
= old
->password
;
1661 info
->older_password
= old
->old_password
;
1664 secrets_debug_domain_info(DBGLVL_INFO
, info
, "join");
1666 status
= secrets_store_domain_info(info
, false /* upgrade */);
1667 if (!NT_STATUS_IS_OK(status
)) {
1668 DBG_ERR("secrets_store_domain_info() failed "
1669 "for %s - %s\n", domain
, nt_errstr(status
));
1670 dbwrap_transaction_cancel(db
);
1675 ret
= dbwrap_transaction_commit(db
);
1677 DBG_ERR("dbwrap_transaction_commit() failed for %s\n",
1680 return NT_STATUS_INTERNAL_DB_ERROR
;
1684 return NT_STATUS_OK
;
1687 NTSTATUS
secrets_prepare_password_change(const char *domain
, const char *dcname
,
1688 const char *cleartext_unix
,
1689 TALLOC_CTX
*mem_ctx
,
1690 struct secrets_domain_info1
**pinfo
,
1691 struct secrets_domain_info1_change
**pprev
)
1693 TALLOC_CTX
*frame
= talloc_stackframe();
1694 struct db_context
*db
= NULL
;
1695 struct secrets_domain_info1
*info
= NULL
;
1696 struct secrets_domain_info1_change
*prev
= NULL
;
1697 struct secrets_domain_info1_change
*next
= NULL
;
1698 struct timeval tv
= timeval_current();
1699 NTTIME now
= timeval_to_nttime(&tv
);
1703 db
= secrets_db_ctx();
1705 ret
= dbwrap_transaction_start(db
);
1707 DBG_ERR("dbwrap_transaction_start() failed for %s\n",
1710 return NT_STATUS_INTERNAL_DB_ERROR
;
1713 status
= secrets_fetch_or_upgrade_domain_info(domain
, frame
, &info
);
1714 if (!NT_STATUS_IS_OK(status
)) {
1715 DBG_ERR("secrets_fetch_or_upgrade_domain_info(%s) failed\n",
1717 dbwrap_transaction_cancel(db
);
1722 prev
= info
->next_change
;
1723 info
->next_change
= NULL
;
1725 next
= talloc_zero(frame
, struct secrets_domain_info1_change
);
1727 DBG_ERR("talloc_zero failed\n");
1729 return NT_STATUS_NO_MEMORY
;
1735 status
= secrets_domain_info_password_create(next
,
1737 info
->salt_principal
,
1740 if (!NT_STATUS_IS_OK(status
)) {
1741 DBG_ERR("secrets_domain_info_password_create(next) failed "
1742 "for %s - %s\n", domain
, nt_errstr(status
));
1743 dbwrap_transaction_cancel(db
);
1749 next
->local_status
= NT_STATUS_OK
;
1750 next
->remote_status
= NT_STATUS_NOT_COMMITTED
;
1751 next
->change_time
= now
;
1752 next
->change_server
= dcname
;
1754 info
->next_change
= next
;
1756 secrets_debug_domain_info(DBGLVL_INFO
, info
, "prepare_change");
1758 status
= secrets_store_domain_info(info
, false /* upgrade */);
1759 if (!NT_STATUS_IS_OK(status
)) {
1760 DBG_ERR("secrets_store_domain_info() failed "
1761 "for %s - %s\n", domain
, nt_errstr(status
));
1762 dbwrap_transaction_cancel(db
);
1768 * We now reparse it.
1770 status
= secrets_fetch_domain_info(domain
, frame
, &info
);
1771 if (!NT_STATUS_IS_OK(status
)) {
1772 DBG_ERR("secrets_fetch_domain_info(%s) failed\n", domain
);
1773 dbwrap_transaction_cancel(db
);
1778 ret
= dbwrap_transaction_commit(db
);
1780 DBG_ERR("dbwrap_transaction_commit() failed for %s\n",
1783 return NT_STATUS_INTERNAL_DB_ERROR
;
1786 *pinfo
= talloc_move(mem_ctx
, &info
);
1788 *pprev
= talloc_move(mem_ctx
, &prev
);
1794 return NT_STATUS_OK
;
1797 static NTSTATUS
secrets_check_password_change(const struct secrets_domain_info1
*cookie
,
1798 TALLOC_CTX
*mem_ctx
,
1799 struct secrets_domain_info1
**pstored
)
1801 const char *domain
= cookie
->domain_info
.name
.string
;
1802 struct secrets_domain_info1
*stored
= NULL
;
1803 struct secrets_domain_info1_change
*sn
= NULL
;
1804 struct secrets_domain_info1_change
*cn
= NULL
;
1808 if (cookie
->next_change
== NULL
) {
1809 DBG_ERR("cookie->next_change == NULL for %s.\n", domain
);
1810 return NT_STATUS_INTERNAL_ERROR
;
1813 if (cookie
->next_change
->password
== NULL
) {
1814 DBG_ERR("cookie->next_change->password == NULL for %s.\n", domain
);
1815 return NT_STATUS_INTERNAL_ERROR
;
1818 if (cookie
->password
== NULL
) {
1819 DBG_ERR("cookie->password == NULL for %s.\n", domain
);
1820 return NT_STATUS_INTERNAL_ERROR
;
1824 * Here we check that the given strucure still contains the
1825 * same secrets_domain_info1_change as currently stored.
1827 * There's always a gap between secrets_prepare_password_change()
1828 * and the callers of secrets_check_password_change().
1831 status
= secrets_fetch_domain_info(domain
, mem_ctx
, &stored
);
1832 if (!NT_STATUS_IS_OK(status
)) {
1833 DBG_ERR("secrets_fetch_domain_info(%s) failed\n", domain
);
1837 if (stored
->next_change
== NULL
) {
1839 * We hit a race..., the administrator
1840 * rejoined or something similar happened.
1842 DBG_ERR("stored->next_change == NULL for %s.\n", domain
);
1843 TALLOC_FREE(stored
);
1844 return NT_STATUS_NETWORK_CREDENTIAL_CONFLICT
;
1847 if (stored
->password_last_change
!= cookie
->password_last_change
) {
1848 struct timeval store_tv
;
1849 struct timeval_buf store_buf
;
1850 struct timeval cookie_tv
;
1851 struct timeval_buf cookie_buf
;
1853 nttime_to_timeval(&store_tv
, stored
->password_last_change
);
1854 nttime_to_timeval(&cookie_tv
, cookie
->password_last_change
);
1856 DBG_ERR("password_last_change differs %s != %s for %s.\n",
1857 timeval_str_buf(&store_tv
, false, false, &store_buf
),
1858 timeval_str_buf(&cookie_tv
, false, false, &cookie_buf
),
1860 TALLOC_FREE(stored
);
1861 return NT_STATUS_NETWORK_CREDENTIAL_CONFLICT
;
1864 sn
= stored
->next_change
;
1865 cn
= cookie
->next_change
;
1867 if (sn
->change_time
!= cn
->change_time
) {
1868 struct timeval store_tv
;
1869 struct timeval_buf store_buf
;
1870 struct timeval cookie_tv
;
1871 struct timeval_buf cookie_buf
;
1873 nttime_to_timeval(&store_tv
, sn
->change_time
);
1874 nttime_to_timeval(&cookie_tv
, cn
->change_time
);
1876 DBG_ERR("next change_time differs %s != %s for %s.\n",
1877 timeval_str_buf(&store_tv
, false, false, &store_buf
),
1878 timeval_str_buf(&cookie_tv
, false, false, &cookie_buf
),
1880 TALLOC_FREE(stored
);
1881 return NT_STATUS_NETWORK_CREDENTIAL_CONFLICT
;
1884 if (sn
->password
->change_time
!= cn
->password
->change_time
) {
1885 struct timeval store_tv
;
1886 struct timeval_buf store_buf
;
1887 struct timeval cookie_tv
;
1888 struct timeval_buf cookie_buf
;
1890 nttime_to_timeval(&store_tv
, sn
->password
->change_time
);
1891 nttime_to_timeval(&cookie_tv
, cn
->password
->change_time
);
1893 DBG_ERR("next password.change_time differs %s != %s for %s.\n",
1894 timeval_str_buf(&store_tv
, false, false, &store_buf
),
1895 timeval_str_buf(&cookie_tv
, false, false, &cookie_buf
),
1897 TALLOC_FREE(stored
);
1898 return NT_STATUS_NETWORK_CREDENTIAL_CONFLICT
;
1901 cmp
= memcmp(sn
->password
->nt_hash
.hash
,
1902 cn
->password
->nt_hash
.hash
,
1905 DBG_ERR("next password.nt_hash differs for %s.\n",
1907 TALLOC_FREE(stored
);
1908 return NT_STATUS_NETWORK_CREDENTIAL_CONFLICT
;
1911 cmp
= memcmp(stored
->password
->nt_hash
.hash
,
1912 cookie
->password
->nt_hash
.hash
,
1915 DBG_ERR("password.nt_hash differs for %s.\n",
1917 TALLOC_FREE(stored
);
1918 return NT_STATUS_NETWORK_CREDENTIAL_CONFLICT
;
1922 return NT_STATUS_OK
;
1925 static NTSTATUS
secrets_abort_password_change(const char *change_server
,
1926 NTSTATUS local_status
,
1927 NTSTATUS remote_status
,
1928 const struct secrets_domain_info1
*cookie
,
1931 const char *domain
= cookie
->domain_info
.name
.string
;
1932 TALLOC_CTX
*frame
= talloc_stackframe();
1933 struct db_context
*db
= NULL
;
1934 struct secrets_domain_info1
*info
= NULL
;
1935 const char *reason
= defer
? "defer_change" : "failed_change";
1936 struct timeval tv
= timeval_current();
1937 NTTIME now
= timeval_to_nttime(&tv
);
1941 db
= secrets_db_ctx();
1943 ret
= dbwrap_transaction_start(db
);
1945 DBG_ERR("dbwrap_transaction_start() failed for %s\n",
1948 return NT_STATUS_INTERNAL_DB_ERROR
;
1952 * secrets_check_password_change()
1953 * checks that cookie->next_change
1954 * is valid and the same as store
1957 status
= secrets_check_password_change(cookie
, frame
, &info
);
1958 if (!NT_STATUS_IS_OK(status
)) {
1959 DBG_ERR("secrets_check_password_change(%s) failed\n", domain
);
1960 dbwrap_transaction_cancel(db
);
1966 * Remember the last server and error.
1968 info
->next_change
->change_server
= change_server
;
1969 info
->next_change
->change_time
= now
;
1970 info
->next_change
->local_status
= local_status
;
1971 info
->next_change
->remote_status
= remote_status
;
1974 * Make sure the next automatic change is deferred.
1977 info
->password_last_change
= now
;
1980 secrets_debug_domain_info(DBGLVL_WARNING
, info
, reason
);
1982 status
= secrets_store_domain_info(info
, false /* upgrade */);
1983 if (!NT_STATUS_IS_OK(status
)) {
1984 DBG_ERR("secrets_store_domain_info() failed "
1985 "for %s - %s\n", domain
, nt_errstr(status
));
1986 dbwrap_transaction_cancel(db
);
1991 ret
= dbwrap_transaction_commit(db
);
1993 DBG_ERR("dbwrap_transaction_commit() failed for %s\n",
1996 return NT_STATUS_INTERNAL_DB_ERROR
;
2000 return NT_STATUS_OK
;
2003 NTSTATUS
secrets_failed_password_change(const char *change_server
,
2004 NTSTATUS local_status
,
2005 NTSTATUS remote_status
,
2006 const struct secrets_domain_info1
*cookie
)
2008 static const bool defer
= false;
2009 return secrets_abort_password_change(change_server
,
2015 NTSTATUS
secrets_defer_password_change(const char *change_server
,
2016 NTSTATUS local_status
,
2017 NTSTATUS remote_status
,
2018 const struct secrets_domain_info1
*cookie
)
2020 static const bool defer
= true;
2021 return secrets_abort_password_change(change_server
,
2027 NTSTATUS
secrets_finish_password_change(const char *change_server
,
2029 const struct secrets_domain_info1
*cookie
)
2031 const char *domain
= cookie
->domain_info
.name
.string
;
2032 TALLOC_CTX
*frame
= talloc_stackframe();
2033 struct db_context
*db
= NULL
;
2034 struct secrets_domain_info1
*info
= NULL
;
2035 struct secrets_domain_info1_change
*nc
= NULL
;
2039 db
= secrets_db_ctx();
2041 ret
= dbwrap_transaction_start(db
);
2043 DBG_ERR("dbwrap_transaction_start() failed for %s\n",
2046 return NT_STATUS_INTERNAL_DB_ERROR
;
2050 * secrets_check_password_change() checks that cookie->next_change is
2051 * valid and the same as store in the database.
2053 status
= secrets_check_password_change(cookie
, frame
, &info
);
2054 if (!NT_STATUS_IS_OK(status
)) {
2055 DBG_ERR("secrets_check_password_change(%s) failed\n", domain
);
2056 dbwrap_transaction_cancel(db
);
2061 nc
= info
->next_change
;
2063 nc
->password
->change_server
= change_server
;
2064 nc
->password
->change_time
= change_time
;
2066 info
->password_last_change
= change_time
;
2067 info
->password_changes
+= 1;
2068 info
->next_change
= NULL
;
2070 info
->older_password
= info
->old_password
;
2071 info
->old_password
= info
->password
;
2072 info
->password
= nc
->password
;
2074 secrets_debug_domain_info(DBGLVL_WARNING
, info
, "finish_change");
2076 status
= secrets_store_domain_info(info
, false /* upgrade */);
2077 if (!NT_STATUS_IS_OK(status
)) {
2078 DBG_ERR("secrets_store_domain_info() failed "
2079 "for %s - %s\n", domain
, nt_errstr(status
));
2080 dbwrap_transaction_cancel(db
);
2085 ret
= dbwrap_transaction_commit(db
);
2087 DBG_ERR("dbwrap_transaction_commit() failed for %s\n",
2090 return NT_STATUS_INTERNAL_DB_ERROR
;
2094 return NT_STATUS_OK
;