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 */
28 #define DBGC_CLASS DBGC_PASSDB
30 static struct db_context
*db_ctx
;
32 /* Urrrg. global.... */
33 bool global_machine_password_needs_changing
;
36 * Use a TDB to store an incrementing random seed.
38 * Initialised to the current pid, the very first time Samba starts,
39 * and incremented by one each time it is needed.
41 * @note Not called by systems with a working /dev/urandom.
43 static void get_rand_seed(int *new_seed
)
45 *new_seed
= sys_getpid();
47 dbwrap_change_int32_atomic(db_ctx
, "INFO/random_seed",
52 /* open up the secrets database */
53 bool secrets_init(void)
61 fname
= talloc_asprintf(talloc_tos(), "%s/secrets.tdb",
67 db_ctx
= db_open_trans(NULL
, fname
, 0,
68 TDB_DEFAULT
, O_RDWR
|O_CREAT
, 0600);
71 DEBUG(0,("Failed to open %s\n", fname
));
79 * Set a reseed function for the crypto random generator
81 * This avoids a problem where systems without /dev/urandom
82 * could send the same challenge to multiple clients
84 set_rand_reseed_callback(get_rand_seed
);
86 /* Ensure that the reseed is done now, while we are root, etc */
87 generate_random_buffer(&dummy
, sizeof(dummy
));
92 struct db_context
*secrets_db_ctx(void)
94 if (!secrets_init()) {
104 void secrets_shutdown(void)
109 /* read a entry from the secrets database - the caller must free the result
110 if size is non-null then the size of the entry is put in there
112 void *secrets_fetch(const char *key
, size_t *size
)
117 if (!secrets_init()) {
121 if (db_ctx
->fetch(db_ctx
, talloc_tos(), string_tdb_data(key
),
126 result
= memdup(dbuf
.dptr
, dbuf
.dsize
);
127 if (result
== NULL
) {
130 TALLOC_FREE(dbuf
.dptr
);
139 /* store a secrets entry
141 bool secrets_store(const char *key
, const void *data
, size_t size
)
145 if (!secrets_init()) {
149 status
= dbwrap_trans_store(db_ctx
, string_tdb_data(key
),
150 make_tdb_data((const uint8
*)data
, size
),
152 return NT_STATUS_IS_OK(status
);
156 /* delete a secets database entry
158 bool secrets_delete(const char *key
)
161 if (!secrets_init()) {
165 status
= dbwrap_trans_delete(db_ctx
, string_tdb_data(key
));
167 return NT_STATUS_IS_OK(status
);
171 * Form a key for fetching the domain sid
173 * @param domain domain name
177 static const char *domain_sid_keystr(const char *domain
)
181 keystr
= talloc_asprintf_strupper_m(talloc_tos(), "%s/%s",
182 SECRETS_DOMAIN_SID
, domain
);
183 SMB_ASSERT(keystr
!= NULL
);
187 bool secrets_store_domain_sid(const char *domain
, const DOM_SID
*sid
)
191 ret
= secrets_store(domain_sid_keystr(domain
), sid
, sizeof(DOM_SID
));
193 /* Force a re-query, in case we modified our domain */
195 reset_global_sam_sid();
199 bool secrets_fetch_domain_sid(const char *domain
, DOM_SID
*sid
)
204 dyn_sid
= (DOM_SID
*)secrets_fetch(domain_sid_keystr(domain
), &size
);
209 if (size
!= sizeof(DOM_SID
)) {
219 bool secrets_store_domain_guid(const char *domain
, struct GUID
*guid
)
223 slprintf(key
, sizeof(key
)-1, "%s/%s", SECRETS_DOMAIN_GUID
, domain
);
225 return secrets_store(key
, guid
, sizeof(struct GUID
));
228 bool secrets_fetch_domain_guid(const char *domain
, struct GUID
*guid
)
230 struct GUID
*dyn_guid
;
233 struct GUID new_guid
;
235 slprintf(key
, sizeof(key
)-1, "%s/%s", SECRETS_DOMAIN_GUID
, domain
);
237 dyn_guid
= (struct GUID
*)secrets_fetch(key
, &size
);
240 if (lp_server_role() == ROLE_DOMAIN_PDC
) {
241 smb_uuid_generate_random(&new_guid
);
242 if (!secrets_store_domain_guid(domain
, &new_guid
))
244 dyn_guid
= (struct GUID
*)secrets_fetch(key
, &size
);
246 if (dyn_guid
== NULL
) {
251 if (size
!= sizeof(struct GUID
)) {
252 DEBUG(1,("UUID size %d is wrong!\n", (int)size
));
263 * Form a key for fetching the machine trust account sec channel type
265 * @param domain domain name
269 static const char *machine_sec_channel_type_keystr(const char *domain
)
273 keystr
= talloc_asprintf_strupper_m(talloc_tos(), "%s/%s",
274 SECRETS_MACHINE_SEC_CHANNEL_TYPE
,
276 SMB_ASSERT(keystr
!= NULL
);
281 * Form a key for fetching the machine trust account last change time
283 * @param domain domain name
287 static const char *machine_last_change_time_keystr(const char *domain
)
291 keystr
= talloc_asprintf_strupper_m(talloc_tos(), "%s/%s",
292 SECRETS_MACHINE_LAST_CHANGE_TIME
,
294 SMB_ASSERT(keystr
!= NULL
);
300 * Form a key for fetching the machine trust account password
302 * @param domain domain name
306 static const char *machine_password_keystr(const char *domain
)
310 keystr
= talloc_asprintf_strupper_m(talloc_tos(), "%s/%s",
311 SECRETS_MACHINE_PASSWORD
, domain
);
312 SMB_ASSERT(keystr
!= NULL
);
317 * Form a key for fetching the machine trust account password
319 * @param domain domain name
321 * @return stored password's key
323 static const char *trust_keystr(const char *domain
)
327 keystr
= talloc_asprintf_strupper_m(talloc_tos(), "%s/%s",
328 SECRETS_MACHINE_ACCT_PASS
, domain
);
329 SMB_ASSERT(keystr
!= NULL
);
334 * Form a key for fetching a trusted domain password
336 * @param domain trusted domain name
338 * @return stored password's key
340 static char *trustdom_keystr(const char *domain
)
344 keystr
= talloc_asprintf_strupper_m(talloc_tos(), "%s/%s",
345 SECRETS_DOMTRUST_ACCT_PASS
,
347 SMB_ASSERT(keystr
!= NULL
);
351 /************************************************************************
352 Lock the trust password entry.
353 ************************************************************************/
355 void *secrets_get_trust_account_lock(TALLOC_CTX
*mem_ctx
, const char *domain
)
357 if (!secrets_init()) {
361 return db_ctx
->fetch_locked(
362 db_ctx
, mem_ctx
, string_term_tdb_data(trust_keystr(domain
)));
365 /************************************************************************
366 Routine to get the default secure channel type for trust accounts
367 ************************************************************************/
369 uint32
get_default_sec_channel(void)
371 if (lp_server_role() == ROLE_DOMAIN_BDC
||
372 lp_server_role() == ROLE_DOMAIN_PDC
) {
375 return SEC_CHAN_WKSTA
;
379 /************************************************************************
380 Routine to get the trust account password for a domain.
381 This only tries to get the legacy hashed version of the password.
382 The user of this function must have locked the trust password file using
383 the above secrets_lock_trust_account_password().
384 ************************************************************************/
386 bool secrets_fetch_trust_account_password_legacy(const char *domain
,
388 time_t *pass_last_set_time
,
391 struct machine_acct_pass
*pass
;
394 if (!(pass
= (struct machine_acct_pass
*)secrets_fetch(
395 trust_keystr(domain
), &size
))) {
396 DEBUG(5, ("secrets_fetch failed!\n"));
400 if (size
!= sizeof(*pass
)) {
401 DEBUG(0, ("secrets were of incorrect size!\n"));
405 if (pass_last_set_time
) {
406 *pass_last_set_time
= pass
->mod_time
;
408 memcpy(ret_pwd
, pass
->hash
, 16);
411 *channel
= get_default_sec_channel();
414 /* Test if machine password has expired and needs to be changed */
415 if (lp_machine_password_timeout()) {
416 if (pass
->mod_time
> 0 && time(NULL
) > (pass
->mod_time
+
417 (time_t)lp_machine_password_timeout())) {
418 global_machine_password_needs_changing
= True
;
426 /************************************************************************
427 Routine to get the trust account password for a domain.
428 The user of this function must have locked the trust password file using
429 the above secrets_lock_trust_account_password().
430 ************************************************************************/
432 bool secrets_fetch_trust_account_password(const char *domain
, uint8 ret_pwd
[16],
433 time_t *pass_last_set_time
,
438 plaintext
= secrets_fetch_machine_password(domain
, pass_last_set_time
,
441 DEBUG(4,("Using cleartext machine password\n"));
442 E_md4hash(plaintext
, ret_pwd
);
443 SAFE_FREE(plaintext
);
447 return secrets_fetch_trust_account_password_legacy(domain
, ret_pwd
,
453 * Pack SID passed by pointer
455 * @param pack_buf pointer to buffer which is to be filled with packed data
456 * @param bufsize size of packing buffer
457 * @param sid pointer to sid to be packed
459 * @return length of the packed representation of the whole structure
461 static size_t tdb_sid_pack(uint8
*pack_buf
, int bufsize
, DOM_SID
* sid
)
466 int remaining_space
= pack_buf
? bufsize
: 0;
472 len
+= tdb_pack(p
, remaining_space
, "bb", sid
->sid_rev_num
,
476 remaining_space
= bufsize
- len
;
479 for (idx
= 0; idx
< 6; idx
++) {
480 len
+= tdb_pack(p
, remaining_space
, "b",
484 remaining_space
= bufsize
- len
;
488 for (idx
= 0; idx
< MAXSUBAUTHS
; idx
++) {
489 len
+= tdb_pack(p
, remaining_space
, "d",
490 sid
->sub_auths
[idx
]);
493 remaining_space
= bufsize
- len
;
501 * Unpack SID into a pointer
503 * @param pack_buf pointer to buffer with packed representation
504 * @param bufsize size of the buffer
505 * @param sid pointer to sid structure to be filled with unpacked data
507 * @return size of structure unpacked from buffer
509 static size_t tdb_sid_unpack(uint8
*pack_buf
, int bufsize
, DOM_SID
* sid
)
513 if (!sid
|| !pack_buf
) return -1;
515 len
+= tdb_unpack(pack_buf
+ len
, bufsize
- len
, "bb",
516 &sid
->sid_rev_num
, &sid
->num_auths
);
518 for (idx
= 0; idx
< 6; idx
++) {
519 len
+= tdb_unpack(pack_buf
+ len
, bufsize
- len
, "b",
523 for (idx
= 0; idx
< MAXSUBAUTHS
; idx
++) {
524 len
+= tdb_unpack(pack_buf
+ len
, bufsize
- len
, "d",
525 &sid
->sub_auths
[idx
]);
532 * Pack TRUSTED_DOM_PASS passed by pointer
534 * @param pack_buf pointer to buffer which is to be filled with packed data
535 * @param bufsize size of the buffer
536 * @param pass pointer to trusted domain password to be packed
538 * @return length of the packed representation of the whole structure
540 static size_t tdb_trusted_dom_pass_pack(uint8
*pack_buf
, int bufsize
,
541 TRUSTED_DOM_PASS
* pass
)
545 int remaining_space
= pack_buf
? bufsize
: 0;
551 /* packing unicode domain name and password */
552 len
+= tdb_pack(p
, remaining_space
, "d",
556 remaining_space
= bufsize
- len
;
559 for (idx
= 0; idx
< 32; idx
++) {
560 len
+= tdb_pack(p
, remaining_space
, "w",
561 pass
->uni_name
[idx
]);
564 remaining_space
= bufsize
- len
;
568 len
+= tdb_pack(p
, remaining_space
, "dPd", pass
->pass_len
,
569 pass
->pass
, pass
->mod_time
);
572 remaining_space
= bufsize
- len
;
575 /* packing SID structure */
576 len
+= tdb_sid_pack(p
, remaining_space
, &pass
->domain_sid
);
579 remaining_space
= bufsize
- len
;
587 * Unpack TRUSTED_DOM_PASS passed by pointer
589 * @param pack_buf pointer to buffer with packed representation
590 * @param bufsize size of the buffer
591 * @param pass pointer to trusted domain password to be filled with unpacked data
593 * @return size of structure unpacked from buffer
595 static size_t tdb_trusted_dom_pass_unpack(uint8
*pack_buf
, int bufsize
,
596 TRUSTED_DOM_PASS
* pass
)
601 if (!pack_buf
|| !pass
) return -1;
603 /* unpack unicode domain name and plaintext password */
604 len
+= tdb_unpack(pack_buf
, bufsize
- len
, "d", &pass
->uni_name_len
);
606 for (idx
= 0; idx
< 32; idx
++)
607 len
+= tdb_unpack(pack_buf
+ len
, bufsize
- len
, "w",
608 &pass
->uni_name
[idx
]);
610 len
+= tdb_unpack(pack_buf
+ len
, bufsize
- len
, "dPd",
611 &pass
->pass_len
, &passp
, &pass
->mod_time
);
613 fstrcpy(pass
->pass
, passp
);
617 /* unpack domain sid */
618 len
+= tdb_sid_unpack(pack_buf
+ len
, bufsize
- len
,
624 /************************************************************************
625 Routine to get account password to trusted domain
626 ************************************************************************/
628 bool secrets_fetch_trusted_domain_password(const char *domain
, char** pwd
,
629 DOM_SID
*sid
, time_t *pass_last_set_time
)
631 struct trusted_dom_pass pass
;
634 /* unpacking structures */
640 /* fetching trusted domain password structure */
641 if (!(pass_buf
= (uint8
*)secrets_fetch(trustdom_keystr(domain
),
643 DEBUG(5, ("secrets_fetch failed!\n"));
647 /* unpack trusted domain password */
648 pass_len
= tdb_trusted_dom_pass_unpack(pass_buf
, size
, &pass
);
651 if (pass_len
!= size
) {
652 DEBUG(5, ("Invalid secrets size. Unpacked data doesn't match trusted_dom_pass structure.\n"));
656 /* the trust's password */
658 *pwd
= SMB_STRDUP(pass
.pass
);
664 /* last change time */
665 if (pass_last_set_time
) *pass_last_set_time
= pass
.mod_time
;
668 if (sid
!= NULL
) sid_copy(sid
, &pass
.domain_sid
);
674 * Routine to store the password for trusted domain
676 * @param domain remote domain name
677 * @param pwd plain text password of trust relationship
678 * @param sid remote domain sid
680 * @return true if succeeded
683 bool secrets_store_trusted_domain_password(const char* domain
, const char* pwd
,
686 smb_ucs2_t
*uni_dom_name
;
689 /* packing structures */
690 uint8
*pass_buf
= NULL
;
693 struct trusted_dom_pass pass
;
696 if (push_ucs2_allocate(&uni_dom_name
, domain
) == (size_t)-1) {
697 DEBUG(0, ("Could not convert domain name %s to unicode\n",
702 strncpy_w(pass
.uni_name
, uni_dom_name
, sizeof(pass
.uni_name
) - 1);
703 pass
.uni_name_len
= strlen_w(uni_dom_name
)+1;
704 SAFE_FREE(uni_dom_name
);
706 /* last change time */
707 pass
.mod_time
= time(NULL
);
709 /* password of the trust */
710 pass
.pass_len
= strlen(pwd
);
711 fstrcpy(pass
.pass
, pwd
);
714 sid_copy(&pass
.domain_sid
, sid
);
716 /* Calculate the length. */
717 pass_len
= tdb_trusted_dom_pass_pack(NULL
, 0, &pass
);
718 pass_buf
= SMB_MALLOC_ARRAY(uint8
, pass_len
);
722 pass_len
= tdb_trusted_dom_pass_pack(pass_buf
, pass_len
, &pass
);
723 ret
= secrets_store(trustdom_keystr(domain
), (void *)pass_buf
,
729 /************************************************************************
730 Routine to delete the plaintext machine account password
731 ************************************************************************/
733 bool secrets_delete_machine_password(const char *domain
)
735 return secrets_delete(machine_password_keystr(domain
));
738 /************************************************************************
739 Routine to delete the plaintext machine account password, sec channel type and
740 last change time from secrets database
741 ************************************************************************/
743 bool secrets_delete_machine_password_ex(const char *domain
)
745 if (!secrets_delete(machine_password_keystr(domain
))) {
748 if (!secrets_delete(machine_sec_channel_type_keystr(domain
))) {
751 return secrets_delete(machine_last_change_time_keystr(domain
));
754 /************************************************************************
755 Routine to delete the domain sid
756 ************************************************************************/
758 bool secrets_delete_domain_sid(const char *domain
)
760 return secrets_delete(domain_sid_keystr(domain
));
763 /************************************************************************
764 Routine to set the plaintext machine account password for a realm
765 the password is assumed to be a null terminated ascii string
766 ************************************************************************/
768 bool secrets_store_machine_password(const char *pass
, const char *domain
, uint32 sec_channel
)
771 uint32 last_change_time
;
772 uint32 sec_channel_type
;
774 ret
= secrets_store(machine_password_keystr(domain
), pass
, strlen(pass
)+1);
778 SIVAL(&last_change_time
, 0, time(NULL
));
779 ret
= secrets_store(machine_last_change_time_keystr(domain
), &last_change_time
, sizeof(last_change_time
));
781 SIVAL(&sec_channel_type
, 0, sec_channel
);
782 ret
= secrets_store(machine_sec_channel_type_keystr(domain
), &sec_channel_type
, sizeof(sec_channel_type
));
787 /************************************************************************
788 Routine to fetch the plaintext machine account password for a realm
789 the password is assumed to be a null terminated ascii string.
790 ************************************************************************/
792 char *secrets_fetch_machine_password(const char *domain
,
793 time_t *pass_last_set_time
,
797 ret
= (char *)secrets_fetch(machine_password_keystr(domain
), NULL
);
799 if (pass_last_set_time
) {
801 uint32
*last_set_time
;
802 last_set_time
= (unsigned int *)secrets_fetch(machine_last_change_time_keystr(domain
), &size
);
804 *pass_last_set_time
= IVAL(last_set_time
,0);
805 SAFE_FREE(last_set_time
);
807 *pass_last_set_time
= 0;
813 uint32
*channel_type
;
814 channel_type
= (unsigned int *)secrets_fetch(machine_sec_channel_type_keystr(domain
), &size
);
816 *channel
= IVAL(channel_type
,0);
817 SAFE_FREE(channel_type
);
819 *channel
= get_default_sec_channel();
826 /************************************************************************
827 Routine to delete the password for trusted domain
828 ************************************************************************/
830 bool trusted_domain_password_delete(const char *domain
)
832 return secrets_delete(trustdom_keystr(domain
));
835 bool secrets_store_ldap_pw(const char* dn
, char* pw
)
840 if (asprintf(&key
, "%s/%s", SECRETS_LDAP_BIND_PW
, dn
) < 0) {
841 DEBUG(0, ("secrets_store_ldap_pw: asprintf failed!\n"));
845 ret
= secrets_store(key
, pw
, strlen(pw
)+1);
851 /*******************************************************************
852 Find the ldap password.
853 ******************************************************************/
855 bool fetch_ldap_pw(char **dn
, char** pw
)
860 *dn
= smb_xstrdup(lp_ldap_admin_dn());
862 if (asprintf(&key
, "%s/%s", SECRETS_LDAP_BIND_PW
, *dn
) < 0) {
864 DEBUG(0, ("fetch_ldap_pw: asprintf failed!\n"));
867 *pw
=(char *)secrets_fetch(key
, &size
);
871 /* Upgrade 2.2 style entry */
873 char* old_style_key
= SMB_STRDUP(*dn
);
875 fstring old_style_pw
;
877 if (!old_style_key
) {
878 DEBUG(0, ("fetch_ldap_pw: strdup failed!\n"));
882 for (p
=old_style_key
; *p
; p
++)
883 if (*p
== ',') *p
= '/';
885 data
=(char *)secrets_fetch(old_style_key
, &size
);
886 if (!size
&& size
< sizeof(old_style_pw
)) {
887 DEBUG(0,("fetch_ldap_pw: neither ldap secret retrieved!\n"));
888 SAFE_FREE(old_style_key
);
893 size
= MIN(size
, sizeof(fstring
)-1);
894 strncpy(old_style_pw
, data
, size
);
895 old_style_pw
[size
] = 0;
899 if (!secrets_store_ldap_pw(*dn
, old_style_pw
)) {
900 DEBUG(0,("fetch_ldap_pw: ldap secret could not be upgraded!\n"));
901 SAFE_FREE(old_style_key
);
905 if (!secrets_delete(old_style_key
)) {
906 DEBUG(0,("fetch_ldap_pw: old ldap secret could not be deleted!\n"));
909 SAFE_FREE(old_style_key
);
911 *pw
= smb_xstrdup(old_style_pw
);
918 * Get trusted domains info from secrets.tdb.
921 struct list_trusted_domains_state
{
923 struct trustdom_info
**domains
;
926 static int list_trusted_domain(struct db_record
*rec
, void *private_data
)
928 const size_t prefix_len
= strlen(SECRETS_DOMTRUST_ACCT_PASS
);
929 size_t packed_size
= 0;
930 struct trusted_dom_pass pass
;
931 struct trustdom_info
*dom_info
;
933 struct list_trusted_domains_state
*state
=
934 (struct list_trusted_domains_state
*)private_data
;
936 if ((rec
->key
.dsize
< prefix_len
)
937 || (strncmp((char *)rec
->key
.dptr
, SECRETS_DOMTRUST_ACCT_PASS
,
942 packed_size
= tdb_trusted_dom_pass_unpack(
943 rec
->value
.dptr
, rec
->value
.dsize
, &pass
);
945 if (rec
->value
.dsize
!= packed_size
) {
946 DEBUG(2, ("Secrets record is invalid!\n"));
950 if (pass
.domain_sid
.num_auths
!= 4) {
951 DEBUG(0, ("SID %s is not a domain sid, has %d "
952 "auths instead of 4\n",
953 sid_string_dbg(&pass
.domain_sid
),
954 pass
.domain_sid
.num_auths
));
958 if (!(dom_info
= TALLOC_P(state
->domains
, struct trustdom_info
))) {
959 DEBUG(0, ("talloc failed\n"));
963 if (pull_ucs2_talloc(dom_info
, &dom_info
->name
,
964 pass
.uni_name
) == (size_t)-1) {
965 DEBUG(2, ("pull_ucs2_talloc failed\n"));
966 TALLOC_FREE(dom_info
);
970 sid_copy(&dom_info
->sid
, &pass
.domain_sid
);
972 ADD_TO_ARRAY(state
->domains
, struct trustdom_info
*, dom_info
,
973 &state
->domains
, &state
->num_domains
);
975 if (state
->domains
== NULL
) {
976 state
->num_domains
= 0;
982 NTSTATUS
secrets_trusted_domains(TALLOC_CTX
*mem_ctx
, uint32
*num_domains
,
983 struct trustdom_info
***domains
)
985 struct list_trusted_domains_state state
;
989 if (db_ctx
== NULL
) {
990 return NT_STATUS_ACCESS_DENIED
;
993 state
.num_domains
= 0;
996 * Make sure that a talloc context for the trustdom_info structs
1000 if (!(state
.domains
= TALLOC_ARRAY(
1001 mem_ctx
, struct trustdom_info
*, 1))) {
1002 return NT_STATUS_NO_MEMORY
;
1005 db_ctx
->traverse_read(db_ctx
, list_trusted_domain
, (void *)&state
);
1007 *num_domains
= state
.num_domains
;
1008 *domains
= state
.domains
;
1009 return NT_STATUS_OK
;
1012 /*******************************************************************************
1013 Store a complete AFS keyfile into secrets.tdb.
1014 *******************************************************************************/
1016 bool secrets_store_afs_keyfile(const char *cell
, const struct afs_keyfile
*keyfile
)
1020 if ((cell
== NULL
) || (keyfile
== NULL
))
1023 if (ntohl(keyfile
->nkeys
) > SECRETS_AFS_MAXKEYS
)
1026 slprintf(key
, sizeof(key
)-1, "%s/%s", SECRETS_AFS_KEYFILE
, cell
);
1027 return secrets_store(key
, keyfile
, sizeof(struct afs_keyfile
));
1030 /*******************************************************************************
1031 Fetch the current (highest) AFS key from secrets.tdb
1032 *******************************************************************************/
1033 bool secrets_fetch_afs_key(const char *cell
, struct afs_key
*result
)
1036 struct afs_keyfile
*keyfile
;
1040 slprintf(key
, sizeof(key
)-1, "%s/%s", SECRETS_AFS_KEYFILE
, cell
);
1042 keyfile
= (struct afs_keyfile
*)secrets_fetch(key
, &size
);
1044 if (keyfile
== NULL
)
1047 if (size
!= sizeof(struct afs_keyfile
)) {
1052 i
= ntohl(keyfile
->nkeys
);
1054 if (i
> SECRETS_AFS_MAXKEYS
) {
1059 *result
= keyfile
->entry
[i
-1];
1061 result
->kvno
= ntohl(result
->kvno
);
1066 /******************************************************************************
1067 When kerberos is not available, choose between anonymous or
1068 authenticated connections.
1070 We need to use an authenticated connection if DCs have the
1071 RestrictAnonymous registry entry set > 0, or the "Additional
1072 restrictions for anonymous connections" set in the win2k Local
1075 Caller to free() result in domain, username, password
1076 *******************************************************************************/
1077 void secrets_fetch_ipc_userpass(char **username
, char **domain
, char **password
)
1079 *username
= (char *)secrets_fetch(SECRETS_AUTH_USER
, NULL
);
1080 *domain
= (char *)secrets_fetch(SECRETS_AUTH_DOMAIN
, NULL
);
1081 *password
= (char *)secrets_fetch(SECRETS_AUTH_PASSWORD
, NULL
);
1083 if (*username
&& **username
) {
1085 if (!*domain
|| !**domain
)
1086 *domain
= smb_xstrdup(lp_workgroup());
1088 if (!*password
|| !**password
)
1089 *password
= smb_xstrdup("");
1091 DEBUG(3, ("IPC$ connections done by user %s\\%s\n",
1092 *domain
, *username
));
1095 DEBUG(3, ("IPC$ connections done anonymously\n"));
1096 *username
= smb_xstrdup("");
1097 *domain
= smb_xstrdup("");
1098 *password
= smb_xstrdup("");
1102 /******************************************************************************
1103 Open or create the schannel session store tdb.
1104 *******************************************************************************/
1106 static TDB_CONTEXT
*open_schannel_session_store(TALLOC_CTX
*mem_ctx
)
1110 TDB_CONTEXT
*tdb_sc
= NULL
;
1111 char *fname
= talloc_asprintf(mem_ctx
, "%s/schannel_store.tdb", lp_private_dir());
1117 tdb_sc
= tdb_open_log(fname
, 0, TDB_DEFAULT
, O_RDWR
|O_CREAT
, 0600);
1120 DEBUG(0,("open_schannel_session_store: Failed to open %s\n", fname
));
1125 vers
= tdb_fetch_bystring(tdb_sc
, "SCHANNEL_STORE_VERSION");
1126 if (vers
.dptr
== NULL
) {
1127 /* First opener, no version. */
1129 vers
.dptr
= (uint8
*)&ver
;
1131 tdb_store_bystring(tdb_sc
, "SCHANNEL_STORE_VERSION", vers
, TDB_REPLACE
);
1133 } else if (vers
.dsize
== 4) {
1134 ver
= IVAL(vers
.dptr
,0);
1138 DEBUG(0,("open_schannel_session_store: wrong version number %d in %s\n",
1144 DEBUG(0,("open_schannel_session_store: wrong version number size %d in %s\n",
1145 (int)vers
.dsize
, fname
));
1148 SAFE_FREE(vers
.dptr
);
1154 /******************************************************************************
1155 Store the schannel state after an AUTH2 call.
1156 Note we must be root here.
1157 *******************************************************************************/
1159 bool secrets_store_schannel_session_info(TALLOC_CTX
*mem_ctx
,
1160 const char *remote_machine
,
1161 const struct dcinfo
*pdc
)
1163 TDB_CONTEXT
*tdb_sc
= NULL
;
1166 char *keystr
= talloc_asprintf_strupper_m(mem_ctx
, "%s/%s",
1167 SECRETS_SCHANNEL_STATE
,
1173 /* Work out how large the record is. */
1174 value
.dsize
= tdb_pack(NULL
, 0, "dBBBBBfff",
1176 8, pdc
->seed_chal
.data
,
1177 8, pdc
->clnt_chal
.data
,
1178 8, pdc
->srv_chal
.data
,
1182 pdc
->remote_machine
,
1185 value
.dptr
= TALLOC_ARRAY(mem_ctx
, uint8
, value
.dsize
);
1187 TALLOC_FREE(keystr
);
1191 value
.dsize
= tdb_pack(value
.dptr
, value
.dsize
, "dBBBBBfff",
1193 8, pdc
->seed_chal
.data
,
1194 8, pdc
->clnt_chal
.data
,
1195 8, pdc
->srv_chal
.data
,
1199 pdc
->remote_machine
,
1202 tdb_sc
= open_schannel_session_store(mem_ctx
);
1204 TALLOC_FREE(keystr
);
1205 TALLOC_FREE(value
.dptr
);
1209 ret
= (tdb_store_bystring(tdb_sc
, keystr
, value
, TDB_REPLACE
) == 0 ? True
: False
);
1211 DEBUG(3,("secrets_store_schannel_session_info: stored schannel info with key %s\n",
1215 TALLOC_FREE(keystr
);
1216 TALLOC_FREE(value
.dptr
);
1220 /******************************************************************************
1221 Restore the schannel state on a client reconnect.
1222 Note we must be root here.
1223 *******************************************************************************/
1225 bool secrets_restore_schannel_session_info(TALLOC_CTX
*mem_ctx
,
1226 const char *remote_machine
,
1227 struct dcinfo
**ppdc
)
1229 TDB_CONTEXT
*tdb_sc
= NULL
;
1231 unsigned char *pseed_chal
= NULL
;
1232 unsigned char *pclnt_chal
= NULL
;
1233 unsigned char *psrv_chal
= NULL
;
1234 unsigned char *psess_key
= NULL
;
1235 unsigned char *pmach_pw
= NULL
;
1236 uint32 l1
, l2
, l3
, l4
, l5
;
1238 struct dcinfo
*pdc
= NULL
;
1239 char *keystr
= talloc_asprintf_strupper_m(mem_ctx
, "%s/%s",
1240 SECRETS_SCHANNEL_STATE
,
1249 tdb_sc
= open_schannel_session_store(mem_ctx
);
1251 TALLOC_FREE(keystr
);
1255 value
= tdb_fetch_bystring(tdb_sc
, keystr
);
1257 DEBUG(0,("secrets_restore_schannel_session_info: Failed to find entry with key %s\n",
1263 pdc
= TALLOC_ZERO_P(mem_ctx
, struct dcinfo
);
1265 /* Retrieve the record. */
1266 ret
= tdb_unpack(value
.dptr
, value
.dsize
, "dBBBBBfff",
1274 &pdc
->remote_machine
,
1277 if (ret
== -1 || l1
!= 8 || l2
!= 8 || l3
!= 8 || l4
!= 16 || l5
!= 16) {
1278 /* Bad record - delete it. */
1279 tdb_delete_bystring(tdb_sc
, keystr
);
1281 TALLOC_FREE(keystr
);
1283 SAFE_FREE(pseed_chal
);
1284 SAFE_FREE(pclnt_chal
);
1285 SAFE_FREE(psrv_chal
);
1286 SAFE_FREE(psess_key
);
1287 SAFE_FREE(pmach_pw
);
1288 SAFE_FREE(value
.dptr
);
1294 memcpy(pdc
->seed_chal
.data
, pseed_chal
, 8);
1295 memcpy(pdc
->clnt_chal
.data
, pclnt_chal
, 8);
1296 memcpy(pdc
->srv_chal
.data
, psrv_chal
, 8);
1297 memcpy(pdc
->sess_key
, psess_key
, 16);
1298 memcpy(pdc
->mach_pw
, pmach_pw
, 16);
1300 /* We know these are true so didn't bother to store them. */
1301 pdc
->challenge_sent
= True
;
1302 pdc
->authenticated
= True
;
1304 DEBUG(3,("secrets_restore_schannel_session_info: restored schannel info key %s\n",
1307 SAFE_FREE(pseed_chal
);
1308 SAFE_FREE(pclnt_chal
);
1309 SAFE_FREE(psrv_chal
);
1310 SAFE_FREE(psess_key
);
1311 SAFE_FREE(pmach_pw
);
1313 TALLOC_FREE(keystr
);
1314 SAFE_FREE(value
.dptr
);
1321 bool secrets_store_generic(const char *owner
, const char *key
, const char *secret
)
1323 char *tdbkey
= NULL
;
1326 if (asprintf(&tdbkey
, "SECRETS/GENERIC/%s/%s", owner
, key
) < 0) {
1327 DEBUG(0, ("asprintf failed!\n"));
1331 ret
= secrets_store(tdbkey
, secret
, strlen(secret
)+1);
1337 /*******************************************************************
1338 Find the ldap password.
1339 ******************************************************************/
1341 char *secrets_fetch_generic(const char *owner
, const char *key
)
1343 char *secret
= NULL
;
1344 char *tdbkey
= NULL
;
1346 if (( ! owner
) || ( ! key
)) {
1347 DEBUG(1, ("Invalid Paramters"));
1351 if (asprintf(&tdbkey
, "SECRETS/GENERIC/%s/%s", owner
, key
) < 0) {
1352 DEBUG(0, ("Out of memory!\n"));
1356 secret
= (char *)secrets_fetch(tdbkey
, NULL
);