2 Unix SMB/CIFS implementation.
3 Authentication utility functions
4 Copyright (C) Andrew Tridgell 1992-1998
5 Copyright (C) Andrew Bartlett 2001
6 Copyright (C) Jeremy Allison 2000-2001
7 Copyright (C) Rafal Szczesniak 2002
9 This program is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 2 of the License, or
12 (at your option) any later version.
14 This program is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
19 You should have received a copy of the GNU General Public License
20 along with this program; if not, write to the Free Software
21 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
27 #define DBGC_CLASS DBGC_AUTH
30 /****************************************************************************
31 Create a UNIX user on demand.
32 ****************************************************************************/
34 static int smb_create_user(const char *domain
, const char *unix_username
, const char *homedir
)
39 pstrcpy(add_script
, lp_adduser_script());
42 all_string_sub(add_script
, "%u", unix_username
, sizeof(pstring
));
44 all_string_sub(add_script
, "%D", domain
, sizeof(pstring
));
46 all_string_sub(add_script
, "%H", homedir
, sizeof(pstring
));
47 ret
= smbrun(add_script
,NULL
);
49 DEBUG(ret
? 0 : 3,("smb_create_user: Running the command `%s' gave %d\n",add_script
,ret
));
53 /****************************************************************************
54 Create a SAM_ACCOUNT - either by looking in the pdb, or by faking it up from
56 ****************************************************************************/
58 NTSTATUS
auth_get_sam_account(const char *user
, SAM_ACCOUNT
**account
)
62 if (!NT_STATUS_IS_OK(nt_status
= pdb_init_sam(account
))) {
67 pdb_ret
= pdb_getsampwnam(*account
, user
);
72 struct passwd
*pass
= Get_Pwnam(user
);
74 return NT_STATUS_NO_SUCH_USER
;
76 if (!NT_STATUS_IS_OK(nt_status
= pdb_fill_sam_pw(*account
, pass
))) {
83 /****************************************************************************
84 Create an auth_usersupplied_data structure
85 ****************************************************************************/
87 static NTSTATUS
make_user_info(auth_usersupplied_info
**user_info
,
89 const char *internal_username
,
90 const char *client_domain
,
92 const char *wksta_name
,
93 DATA_BLOB
*lm_pwd
, DATA_BLOB
*nt_pwd
,
94 DATA_BLOB
*lm_interactive_pwd
, DATA_BLOB
*nt_interactive_pwd
,
99 DEBUG(5,("attempting to make a user_info for %s (%s)\n", internal_username
, smb_name
));
101 *user_info
= SMB_MALLOC_P(auth_usersupplied_info
);
103 DEBUG(0,("malloc failed for user_info (size %lu)\n", (unsigned long)sizeof(*user_info
)));
104 return NT_STATUS_NO_MEMORY
;
107 ZERO_STRUCTP(*user_info
);
109 DEBUG(5,("making strings for %s's user_info struct\n", internal_username
));
111 (*user_info
)->smb_name
.str
= SMB_STRDUP(smb_name
);
112 if ((*user_info
)->smb_name
.str
) {
113 (*user_info
)->smb_name
.len
= strlen(smb_name
);
115 free_user_info(user_info
);
116 return NT_STATUS_NO_MEMORY
;
119 (*user_info
)->internal_username
.str
= SMB_STRDUP(internal_username
);
120 if ((*user_info
)->internal_username
.str
) {
121 (*user_info
)->internal_username
.len
= strlen(internal_username
);
123 free_user_info(user_info
);
124 return NT_STATUS_NO_MEMORY
;
127 (*user_info
)->domain
.str
= SMB_STRDUP(domain
);
128 if ((*user_info
)->domain
.str
) {
129 (*user_info
)->domain
.len
= strlen(domain
);
131 free_user_info(user_info
);
132 return NT_STATUS_NO_MEMORY
;
135 (*user_info
)->client_domain
.str
= SMB_STRDUP(client_domain
);
136 if ((*user_info
)->client_domain
.str
) {
137 (*user_info
)->client_domain
.len
= strlen(client_domain
);
139 free_user_info(user_info
);
140 return NT_STATUS_NO_MEMORY
;
143 (*user_info
)->wksta_name
.str
= SMB_STRDUP(wksta_name
);
144 if ((*user_info
)->wksta_name
.str
) {
145 (*user_info
)->wksta_name
.len
= strlen(wksta_name
);
147 free_user_info(user_info
);
148 return NT_STATUS_NO_MEMORY
;
151 DEBUG(5,("making blobs for %s's user_info struct\n", internal_username
));
154 (*user_info
)->lm_resp
= data_blob(lm_pwd
->data
, lm_pwd
->length
);
156 (*user_info
)->nt_resp
= data_blob(nt_pwd
->data
, nt_pwd
->length
);
157 if (lm_interactive_pwd
)
158 (*user_info
)->lm_interactive_pwd
= data_blob(lm_interactive_pwd
->data
, lm_interactive_pwd
->length
);
159 if (nt_interactive_pwd
)
160 (*user_info
)->nt_interactive_pwd
= data_blob(nt_interactive_pwd
->data
, nt_interactive_pwd
->length
);
163 (*user_info
)->plaintext_password
= data_blob(plaintext
->data
, plaintext
->length
);
165 (*user_info
)->encrypted
= encrypted
;
167 DEBUG(10,("made an %sencrypted user_info for %s (%s)\n", encrypted
? "":"un" , internal_username
, smb_name
));
172 /****************************************************************************
173 Create an auth_usersupplied_data structure after appropriate mapping.
174 ****************************************************************************/
176 NTSTATUS
make_user_info_map(auth_usersupplied_info
**user_info
,
177 const char *smb_name
,
178 const char *client_domain
,
179 const char *wksta_name
,
180 DATA_BLOB
*lm_pwd
, DATA_BLOB
*nt_pwd
,
181 DATA_BLOB
*lm_interactive_pwd
, DATA_BLOB
*nt_interactive_pwd
,
182 DATA_BLOB
*plaintext
,
186 fstring internal_username
;
187 fstrcpy(internal_username
, smb_name
);
188 map_username(internal_username
);
190 DEBUG(5, ("make_user_info_map: Mapping user [%s]\\[%s] from workstation [%s]\n",
191 client_domain
, smb_name
, wksta_name
));
193 /* don't allow "" as a domain, fixes a Win9X bug
194 where it doens't supply a domain for logon script
195 'net use' commands. */
197 if ( *client_domain
)
198 domain
= client_domain
;
200 domain
= lp_workgroup();
202 /* do what win2k does. Always map unknown domains to our own
203 and let the "passdb backend" handle unknown users. */
205 if ( !is_trusted_domain(domain
) && !strequal(domain
, get_global_sam_name()) )
206 domain
= get_default_sam_name();
208 /* we know that it is a trusted domain (and we are allowing them) or it is our domain */
210 return make_user_info(user_info
, smb_name
, internal_username
,
211 client_domain
, domain
, wksta_name
,
213 lm_interactive_pwd
, nt_interactive_pwd
,
214 plaintext
, encrypted
);
217 /****************************************************************************
218 Create an auth_usersupplied_data, making the DATA_BLOBs here.
219 Decrypt and encrypt the passwords.
220 ****************************************************************************/
222 BOOL
make_user_info_netlogon_network(auth_usersupplied_info
**user_info
,
223 const char *smb_name
,
224 const char *client_domain
,
225 const char *wksta_name
,
226 const uchar
*lm_network_pwd
, int lm_pwd_len
,
227 const uchar
*nt_network_pwd
, int nt_pwd_len
)
231 DATA_BLOB lm_blob
= data_blob(lm_network_pwd
, lm_pwd_len
);
232 DATA_BLOB nt_blob
= data_blob(nt_network_pwd
, nt_pwd_len
);
234 nt_status
= make_user_info_map(user_info
,
235 smb_name
, client_domain
,
237 lm_pwd_len
? &lm_blob
: NULL
,
238 nt_pwd_len
? &nt_blob
: NULL
,
242 ret
= NT_STATUS_IS_OK(nt_status
) ? True
: False
;
244 data_blob_free(&lm_blob
);
245 data_blob_free(&nt_blob
);
249 /****************************************************************************
250 Create an auth_usersupplied_data, making the DATA_BLOBs here.
251 Decrypt and encrypt the passwords.
252 ****************************************************************************/
254 BOOL
make_user_info_netlogon_interactive(auth_usersupplied_info
**user_info
,
255 const char *smb_name
,
256 const char *client_domain
,
257 const char *wksta_name
,
259 const uchar lm_interactive_pwd
[16],
260 const uchar nt_interactive_pwd
[16],
261 const uchar
*dc_sess_key
)
265 unsigned char local_lm_response
[24];
266 unsigned char local_nt_response
[24];
267 unsigned char key
[16];
270 memcpy(key
, dc_sess_key
, 8);
272 if (lm_interactive_pwd
) memcpy(lm_pwd
, lm_interactive_pwd
, sizeof(lm_pwd
));
273 if (nt_interactive_pwd
) memcpy(nt_pwd
, nt_interactive_pwd
, sizeof(nt_pwd
));
275 #ifdef DEBUG_PASSWORD
277 dump_data(100, (char *)key
, sizeof(key
));
279 DEBUG(100,("lm owf password:"));
280 dump_data(100, lm_pwd
, sizeof(lm_pwd
));
282 DEBUG(100,("nt owf password:"));
283 dump_data(100, nt_pwd
, sizeof(nt_pwd
));
286 if (lm_interactive_pwd
)
287 SamOEMhash((uchar
*)lm_pwd
, key
, sizeof(lm_pwd
));
289 if (nt_interactive_pwd
)
290 SamOEMhash((uchar
*)nt_pwd
, key
, sizeof(nt_pwd
));
292 #ifdef DEBUG_PASSWORD
293 DEBUG(100,("decrypt of lm owf password:"));
294 dump_data(100, lm_pwd
, sizeof(lm_pwd
));
296 DEBUG(100,("decrypt of nt owf password:"));
297 dump_data(100, nt_pwd
, sizeof(nt_pwd
));
300 if (lm_interactive_pwd
)
301 SMBOWFencrypt((const unsigned char *)lm_pwd
, chal
, local_lm_response
);
303 if (nt_interactive_pwd
)
304 SMBOWFencrypt((const unsigned char *)nt_pwd
, chal
, local_nt_response
);
306 /* Password info paranoia */
312 DATA_BLOB local_lm_blob
;
313 DATA_BLOB local_nt_blob
;
315 DATA_BLOB lm_interactive_blob
;
316 DATA_BLOB nt_interactive_blob
;
318 if (lm_interactive_pwd
) {
319 local_lm_blob
= data_blob(local_lm_response
, sizeof(local_lm_response
));
320 lm_interactive_blob
= data_blob(lm_pwd
, sizeof(lm_pwd
));
324 if (nt_interactive_pwd
) {
325 local_nt_blob
= data_blob(local_nt_response
, sizeof(local_nt_response
));
326 nt_interactive_blob
= data_blob(nt_pwd
, sizeof(nt_pwd
));
330 nt_status
= make_user_info_map(user_info
,
331 smb_name
, client_domain
,
333 lm_interactive_pwd
? &local_lm_blob
: NULL
,
334 nt_interactive_pwd
? &local_nt_blob
: NULL
,
335 lm_interactive_pwd
? &lm_interactive_blob
: NULL
,
336 nt_interactive_pwd
? &nt_interactive_blob
: NULL
,
340 ret
= NT_STATUS_IS_OK(nt_status
) ? True
: False
;
341 data_blob_free(&local_lm_blob
);
342 data_blob_free(&local_nt_blob
);
343 data_blob_free(&lm_interactive_blob
);
344 data_blob_free(&nt_interactive_blob
);
350 /****************************************************************************
351 Create an auth_usersupplied_data structure
352 ****************************************************************************/
354 BOOL
make_user_info_for_reply(auth_usersupplied_info
**user_info
,
355 const char *smb_name
,
356 const char *client_domain
,
358 DATA_BLOB plaintext_password
)
361 DATA_BLOB local_lm_blob
;
362 DATA_BLOB local_nt_blob
;
363 NTSTATUS ret
= NT_STATUS_UNSUCCESSFUL
;
366 * Not encrypted - do so.
369 DEBUG(5,("make_user_info_for_reply: User passwords not in encrypted format.\n"));
371 if (plaintext_password
.data
) {
372 unsigned char local_lm_response
[24];
374 #ifdef DEBUG_PASSWORD
375 DEBUG(10,("Unencrypted password (len %d):\n",plaintext_password
.length
));
376 dump_data(100, plaintext_password
.data
, plaintext_password
.length
);
379 SMBencrypt( (const char *)plaintext_password
.data
, (const uchar
*)chal
, local_lm_response
);
380 local_lm_blob
= data_blob(local_lm_response
, 24);
382 /* We can't do an NT hash here, as the password needs to be
384 local_nt_blob
= data_blob(NULL
, 0);
387 local_lm_blob
= data_blob(NULL
, 0);
388 local_nt_blob
= data_blob(NULL
, 0);
391 ret
= make_user_info_map(user_info
, smb_name
,
393 get_remote_machine_name(),
394 local_lm_blob
.data
? &local_lm_blob
: NULL
,
395 local_nt_blob
.data
? &local_nt_blob
: NULL
,
397 plaintext_password
.data
? &plaintext_password
: NULL
,
400 data_blob_free(&local_lm_blob
);
401 return NT_STATUS_IS_OK(ret
) ? True
: False
;
404 /****************************************************************************
405 Create an auth_usersupplied_data structure
406 ****************************************************************************/
408 NTSTATUS
make_user_info_for_reply_enc(auth_usersupplied_info
**user_info
,
409 const char *smb_name
,
410 const char *client_domain
,
411 DATA_BLOB lm_resp
, DATA_BLOB nt_resp
)
413 return make_user_info_map(user_info
, smb_name
,
415 get_remote_machine_name(),
416 lm_resp
.data
? &lm_resp
: NULL
,
417 nt_resp
.data
? &nt_resp
: NULL
,
422 /****************************************************************************
423 Create a guest user_info blob, for anonymous authenticaion.
424 ****************************************************************************/
426 BOOL
make_user_info_guest(auth_usersupplied_info
**user_info
)
430 nt_status
= make_user_info(user_info
,
439 return NT_STATUS_IS_OK(nt_status
) ? True
: False
;
442 /****************************************************************************
443 prints a NT_USER_TOKEN to debug output.
444 ****************************************************************************/
446 void debug_nt_user_token(int dbg_class
, int dbg_lev
, NT_USER_TOKEN
*token
)
452 DEBUGC(dbg_class
, dbg_lev
, ("NT user token: (NULL)\n"));
456 DEBUGC(dbg_class
, dbg_lev
, ("NT user token of user %s\n",
457 sid_to_string(sid_str
, &token
->user_sids
[0]) ));
458 DEBUGADDC(dbg_class
, dbg_lev
, ("contains %lu SIDs\n", (unsigned long)token
->num_sids
));
459 for (i
= 0; i
< token
->num_sids
; i
++)
460 DEBUGADDC(dbg_class
, dbg_lev
, ("SID[%3lu]: %s\n", (unsigned long)i
,
461 sid_to_string(sid_str
, &token
->user_sids
[i
])));
463 dump_se_priv( dbg_class
, dbg_lev
, &token
->privileges
);
466 /****************************************************************************
467 prints a UNIX 'token' to debug output.
468 ****************************************************************************/
470 void debug_unix_user_token(int dbg_class
, int dbg_lev
, uid_t uid
, gid_t gid
, int n_groups
, gid_t
*groups
)
473 DEBUGC(dbg_class
, dbg_lev
, ("UNIX token of user %ld\n", (long int)uid
));
475 DEBUGADDC(dbg_class
, dbg_lev
, ("Primary group is %ld and contains %i supplementary groups\n", (long int)gid
, n_groups
));
476 for (i
= 0; i
< n_groups
; i
++)
477 DEBUGADDC(dbg_class
, dbg_lev
, ("Group[%3i]: %ld\n", i
,
478 (long int)groups
[i
]));
481 /****************************************************************************
482 Create the SID list for this user.
483 ****************************************************************************/
485 static NTSTATUS
create_nt_user_token(const DOM_SID
*user_sid
, const DOM_SID
*group_sid
,
486 int n_groupSIDs
, DOM_SID
*groupSIDs
,
487 BOOL is_guest
, NT_USER_TOKEN
**token
)
489 NTSTATUS nt_status
= NT_STATUS_OK
;
490 NT_USER_TOKEN
*ptoken
;
494 if ((ptoken
= SMB_MALLOC_P(NT_USER_TOKEN
)) == NULL
) {
495 DEBUG(0, ("create_nt_token: Out of memory allocating token\n"));
496 nt_status
= NT_STATUS_NO_MEMORY
;
500 ZERO_STRUCTP(ptoken
);
502 ptoken
->num_sids
= n_groupSIDs
+ 5;
504 if ((ptoken
->user_sids
= SMB_MALLOC_ARRAY( DOM_SID
, ptoken
->num_sids
)) == NULL
) {
505 DEBUG(0, ("create_nt_token: Out of memory allocating SIDs\n"));
506 nt_status
= NT_STATUS_NO_MEMORY
;
510 memset((char*)ptoken
->user_sids
,0,sizeof(DOM_SID
) * ptoken
->num_sids
);
513 * Note - user SID *MUST* be first in token !
514 * se_access_check depends on this.
516 * Primary group SID is second in token. Convention.
519 sid_copy(&ptoken
->user_sids
[PRIMARY_USER_SID_INDEX
], user_sid
);
521 sid_copy(&ptoken
->user_sids
[PRIMARY_GROUP_SID_INDEX
], group_sid
);
524 * Finally add the "standard" SIDs.
525 * The only difference between guest and "anonymous" (which we
526 * don't really support) is the addition of Authenticated_Users.
529 sid_copy(&ptoken
->user_sids
[2], &global_sid_World
);
530 sid_copy(&ptoken
->user_sids
[3], &global_sid_Network
);
533 sid_copy(&ptoken
->user_sids
[4], &global_sid_Builtin_Guests
);
535 sid_copy(&ptoken
->user_sids
[4], &global_sid_Authenticated_Users
);
537 sid_ndx
= 5; /* next available spot */
539 for (i
= 0; i
< n_groupSIDs
; i
++) {
540 size_t check_sid_idx
;
541 for (check_sid_idx
= 1; check_sid_idx
< ptoken
->num_sids
; check_sid_idx
++) {
542 if (sid_equal(&ptoken
->user_sids
[check_sid_idx
],
548 if (check_sid_idx
>= ptoken
->num_sids
) /* Not found already */ {
549 sid_copy(&ptoken
->user_sids
[sid_ndx
++], &groupSIDs
[i
]);
555 /* add privileges assigned to this user */
557 get_privileges_for_sids( &ptoken
->privileges
, ptoken
->user_sids
, ptoken
->num_sids
);
559 debug_nt_user_token(DBGC_AUTH
, 10, ptoken
);
561 if ((lp_log_nt_token_command() != NULL
) &&
562 (strlen(lp_log_nt_token_command()) > 0)) {
566 char *user_sidstr
, *group_sidstr
;
568 mem_ctx
= talloc_init("setnttoken");
570 return NT_STATUS_NO_MEMORY
;
572 sid_to_string(sidstr
, &ptoken
->user_sids
[0]);
573 user_sidstr
= talloc_strdup(mem_ctx
, sidstr
);
575 group_sidstr
= talloc_strdup(mem_ctx
, "");
576 for (i
=1; i
<ptoken
->num_sids
; i
++) {
577 sid_to_string(sidstr
, &ptoken
->user_sids
[i
]);
578 group_sidstr
= talloc_asprintf(mem_ctx
, "%s %s",
579 group_sidstr
, sidstr
);
582 command
= SMB_STRDUP(lp_log_nt_token_command());
583 command
= realloc_string_sub(command
, "%s", user_sidstr
);
584 command
= realloc_string_sub(command
, "%t", group_sidstr
);
585 DEBUG(8, ("running command: [%s]\n", command
));
586 if (smbrun(command
, NULL
) != 0) {
587 DEBUG(0, ("Could not log NT token\n"));
588 nt_status
= NT_STATUS_ACCESS_DENIED
;
590 talloc_destroy(mem_ctx
);
599 /****************************************************************************
600 Create the SID list for this user.
601 ****************************************************************************/
603 NT_USER_TOKEN
*create_nt_token(uid_t uid
, gid_t gid
, int ngroups
, gid_t
*groups
, BOOL is_guest
)
608 NT_USER_TOKEN
*token
;
611 if (!NT_STATUS_IS_OK(uid_to_sid(&user_sid
, uid
))) {
614 if (!NT_STATUS_IS_OK(gid_to_sid(&group_sid
, gid
))) {
618 group_sids
= SMB_MALLOC_ARRAY(DOM_SID
, ngroups
);
620 DEBUG(0, ("create_nt_token: malloc() failed for DOM_SID list!\n"));
624 for (i
= 0; i
< ngroups
; i
++) {
625 if (!NT_STATUS_IS_OK(gid_to_sid(&(group_sids
)[i
], (groups
)[i
]))) {
626 DEBUG(1, ("create_nt_token: failed to convert gid %ld to a sid!\n", (long int)groups
[i
]));
627 SAFE_FREE(group_sids
);
632 if (!NT_STATUS_IS_OK(create_nt_user_token(&user_sid
, &group_sid
,
633 ngroups
, group_sids
, is_guest
, &token
))) {
634 SAFE_FREE(group_sids
);
638 SAFE_FREE(group_sids
);
643 /******************************************************************************
644 * this function returns the groups (SIDs) of the local SAM the user is in.
645 * If this samba server is a DC of the domain the user belongs to, it returns
646 * both domain groups and local / builtin groups. If the user is in a trusted
647 * domain, or samba is a member server of a domain, then this function returns
648 * local and builtin groups the user is a member of.
650 * currently this is a hack, as there is no sam implementation that is capable
653 * NOTE!! This function will fail if you pass in a winbind user without
655 ******************************************************************************/
657 static NTSTATUS
get_user_groups(const char *username
, uid_t uid
, gid_t gid
,
658 int *n_groups
, DOM_SID
**groups
, gid_t
**unix_groups
)
666 if (strchr(username
, *lp_winbind_separator()) == NULL
) {
670 result
= pdb_enum_group_memberships(username
, gid
, groups
,
671 unix_groups
, n_groups
);
676 /* We have the separator, this must be winbind */
678 n_unix_groups
= winbind_getgroups( username
, unix_groups
);
680 DEBUG(10,("get_user_groups: winbind_getgroups(%s): result = %s\n",
681 username
, n_unix_groups
== -1 ? "FAIL" : "SUCCESS"));
683 if ( n_unix_groups
== -1 )
684 return NT_STATUS_NO_SUCH_USER
; /* what should this return
687 debug_unix_user_token(DBGC_CLASS
, 5, uid
, gid
, n_unix_groups
, *unix_groups
);
689 /* now setup the space for storing the SIDS */
691 if (n_unix_groups
> 0) {
693 *groups
= SMB_MALLOC_ARRAY(DOM_SID
, n_unix_groups
);
696 DEBUG(0, ("get_user_group: malloc() failed for DOM_SID list!\n"));
697 SAFE_FREE(*unix_groups
);
698 return NT_STATUS_NO_MEMORY
;
702 *n_groups
= n_unix_groups
;
704 for (i
= 0; i
< *n_groups
; i
++) {
705 if (!NT_STATUS_IS_OK(gid_to_sid(&(*groups
)[i
], (*unix_groups
)[i
]))) {
706 DEBUG(1, ("get_user_groups: failed to convert gid %ld to a sid!\n",
707 (long int)(*unix_groups
)[i
+1]));
709 SAFE_FREE(*unix_groups
);
710 return NT_STATUS_NO_SUCH_USER
;
717 /***************************************************************************
718 Make a user_info struct
719 ***************************************************************************/
721 static NTSTATUS
make_server_info(auth_serversupplied_info
**server_info
)
723 *server_info
= SMB_MALLOC_P(auth_serversupplied_info
);
725 DEBUG(0,("make_server_info: malloc failed!\n"));
726 return NT_STATUS_NO_MEMORY
;
728 ZERO_STRUCTP(*server_info
);
730 /* Initialise the uid and gid values to something non-zero
731 which may save us from giving away root access if there
732 is a bug in allocating these fields. */
734 (*server_info
)->uid
= -1;
735 (*server_info
)->gid
= -1;
740 /***************************************************************************
741 Fill a server_info struct from a SAM_ACCOUNT with their groups
742 ***************************************************************************/
744 static NTSTATUS
add_user_groups(auth_serversupplied_info
**server_info
,
745 const char * unix_username
,
746 SAM_ACCOUNT
*sampass
,
747 uid_t uid
, gid_t gid
)
750 const DOM_SID
*user_sid
= pdb_get_user_sid(sampass
);
751 const DOM_SID
*group_sid
= pdb_get_group_sid(sampass
);
753 DOM_SID
*groupSIDs
= NULL
;
754 gid_t
*unix_groups
= NULL
;
755 NT_USER_TOKEN
*token
;
759 nt_status
= get_user_groups(unix_username
, uid
, gid
,
760 &n_groupSIDs
, &groupSIDs
, &unix_groups
);
762 if (!NT_STATUS_IS_OK(nt_status
)) {
763 DEBUG(4,("get_user_groups_from_local_sam failed\n"));
764 free_server_info(server_info
);
768 is_guest
= (sid_peek_rid(user_sid
, &rid
) && rid
== DOMAIN_USER_RID_GUEST
);
770 if (!NT_STATUS_IS_OK(nt_status
= create_nt_user_token(user_sid
, group_sid
,
771 n_groupSIDs
, groupSIDs
, is_guest
,
774 DEBUG(4,("create_nt_user_token failed\n"));
775 SAFE_FREE(groupSIDs
);
776 SAFE_FREE(unix_groups
);
777 free_server_info(server_info
);
781 SAFE_FREE(groupSIDs
);
783 (*server_info
)->n_groups
= n_groupSIDs
;
784 (*server_info
)->groups
= unix_groups
;
785 (*server_info
)->ptok
= token
;
790 /***************************************************************************
791 Make (and fill) a user_info struct from a SAM_ACCOUNT
792 ***************************************************************************/
794 NTSTATUS
make_server_info_sam(auth_serversupplied_info
**server_info
,
795 SAM_ACCOUNT
*sampass
)
800 if (!NT_STATUS_IS_OK(nt_status
= make_server_info(server_info
)))
803 (*server_info
)->sam_account
= sampass
;
805 if ( !(pwd
= getpwnam_alloc(pdb_get_username(sampass
))) ) {
806 DEBUG(1, ("User %s in passdb, but getpwnam() fails!\n",
807 pdb_get_username(sampass
)));
808 free_server_info(server_info
);
809 return NT_STATUS_NO_SUCH_USER
;
811 (*server_info
)->unix_name
= smb_xstrdup(pwd
->pw_name
);
812 (*server_info
)->gid
= pwd
->pw_gid
;
813 (*server_info
)->uid
= pwd
->pw_uid
;
817 if (!NT_STATUS_IS_OK(nt_status
= add_user_groups(server_info
, pdb_get_username(sampass
),
820 (*server_info
)->gid
)))
822 free_server_info(server_info
);
826 (*server_info
)->sam_fill_level
= SAM_FILL_ALL
;
827 DEBUG(5,("make_server_info_sam: made server info for user %s -> %s\n",
828 pdb_get_username(sampass
),
829 (*server_info
)->unix_name
));
834 /***************************************************************************
835 Make (and fill) a user_info struct from a 'struct passwd' by conversion
837 ***************************************************************************/
839 NTSTATUS
make_server_info_pw(auth_serversupplied_info
**server_info
,
844 SAM_ACCOUNT
*sampass
= NULL
;
845 if (!NT_STATUS_IS_OK(nt_status
= pdb_init_sam_pw(&sampass
, pwd
))) {
848 if (!NT_STATUS_IS_OK(nt_status
= make_server_info(server_info
))) {
852 (*server_info
)->sam_account
= sampass
;
854 if (!NT_STATUS_IS_OK(nt_status
= add_user_groups(server_info
, unix_username
,
855 sampass
, pwd
->pw_uid
, pwd
->pw_gid
)))
860 (*server_info
)->unix_name
= smb_xstrdup(unix_username
);
862 (*server_info
)->sam_fill_level
= SAM_FILL_ALL
;
863 (*server_info
)->uid
= pwd
->pw_uid
;
864 (*server_info
)->gid
= pwd
->pw_gid
;
868 /***************************************************************************
869 Make (and fill) a user_info struct for a guest login.
870 ***************************************************************************/
872 static NTSTATUS
make_new_server_info_guest(auth_serversupplied_info
**server_info
)
875 SAM_ACCOUNT
*sampass
= NULL
;
878 if (!NT_STATUS_IS_OK(nt_status
= pdb_init_sam(&sampass
))) {
882 sid_copy(&guest_sid
, get_global_sam_sid());
883 sid_append_rid(&guest_sid
, DOMAIN_USER_RID_GUEST
);
886 if (!pdb_getsampwsid(sampass
, &guest_sid
)) {
888 return NT_STATUS_NO_SUCH_USER
;
892 nt_status
= make_server_info_sam(server_info
, sampass
);
894 if (NT_STATUS_IS_OK(nt_status
)) {
895 static const char zeros
[16];
896 (*server_info
)->guest
= True
;
898 /* annoying, but the Guest really does have a session key,
899 and it is all zeros! */
900 (*server_info
)->user_session_key
= data_blob(zeros
, sizeof(zeros
));
901 (*server_info
)->lm_session_key
= data_blob(zeros
, sizeof(zeros
));
907 static auth_serversupplied_info
*copy_serverinfo(auth_serversupplied_info
*src
)
909 auth_serversupplied_info
*dst
;
911 if (!NT_STATUS_IS_OK(make_server_info(&dst
)))
914 dst
->guest
= src
->guest
;
917 dst
->n_groups
= src
->n_groups
;
918 if (src
->n_groups
!= 0)
919 dst
->groups
= memdup(src
->groups
, sizeof(gid_t
)*dst
->n_groups
);
922 dst
->ptok
= dup_nt_token(src
->ptok
);
923 dst
->user_session_key
= data_blob(src
->user_session_key
.data
,
924 src
->user_session_key
.length
);
925 dst
->lm_session_key
= data_blob(src
->lm_session_key
.data
,
926 src
->lm_session_key
.length
);
927 pdb_copy_sam_account(src
->sam_account
, &dst
->sam_account
);
928 dst
->pam_handle
= NULL
;
929 dst
->unix_name
= smb_xstrdup(src
->unix_name
);
934 static auth_serversupplied_info
*guest_info
= NULL
;
936 BOOL
init_guest_info(void)
938 if (guest_info
!= NULL
)
941 return NT_STATUS_IS_OK(make_new_server_info_guest(&guest_info
));
944 NTSTATUS
make_server_info_guest(auth_serversupplied_info
**server_info
)
946 *server_info
= copy_serverinfo(guest_info
);
947 return (*server_info
!= NULL
) ? NT_STATUS_OK
: NT_STATUS_NO_MEMORY
;
950 /***************************************************************************
951 Purely internal function for make_server_info_info3
952 Fill the sam account from getpwnam
953 ***************************************************************************/
954 static NTSTATUS
fill_sam_account(TALLOC_CTX
*mem_ctx
,
956 const char *username
,
957 char **found_username
,
958 uid_t
*uid
, gid_t
*gid
,
959 SAM_ACCOUNT
**sam_account
)
962 fstring dom_user
, lower_username
;
963 fstring real_username
;
964 struct passwd
*passwd
;
966 fstrcpy( lower_username
, username
);
967 strlower_m( lower_username
);
969 fstr_sprintf(dom_user
, "%s%c%s", domain
, *lp_winbind_separator(),
972 /* get the passwd struct but don't create the user if he/she
973 does not exist. We were explicitly called from a following
974 a winbindd authentication request so we should assume that
975 nss_winbindd is working */
977 map_username( dom_user
);
979 if ( !(passwd
= smb_getpwnam( dom_user
, real_username
, True
)) )
980 return NT_STATUS_NO_SUCH_USER
;
982 *uid
= passwd
->pw_uid
;
983 *gid
= passwd
->pw_gid
;
985 /* This is pointless -- there is no suport for differing
986 unix and windows names. Make sure to always store the
987 one we actually looked up and succeeded. Have I mentioned
988 why I hate the 'winbind use default domain' parameter?
991 *found_username
= talloc_strdup( mem_ctx
, real_username
);
993 DEBUG(5,("fill_sam_account: located username was [%s]\n",
996 nt_status
= pdb_init_sam_pw(sam_account
, passwd
);
997 passwd_free(&passwd
);
1001 /****************************************************************************
1002 Wrapper to allow the getpwnam() call to strip the domain name and
1003 try again in case a local UNIX user is already there. Also run through
1004 the username if we fallback to the username only.
1005 ****************************************************************************/
1007 struct passwd
*smb_getpwnam( char *domuser
, fstring save_username
, BOOL create
)
1009 struct passwd
*pw
= NULL
;
1013 /* we only save a copy of the username it has been mangled
1014 by winbindd use default domain */
1016 save_username
[0] = '\0';
1018 /* don't call map_username() here since it has to be done higher
1019 up the stack so we don't call it mutliple times */
1021 fstrcpy( username
, domuser
);
1023 p
= strchr_m( username
, *lp_winbind_separator() );
1025 /* code for a DOMAIN\user string */
1028 fstring strip_username
;
1030 pw
= Get_Pwnam_alloc( domuser
);
1032 /* make sure we get the case of the username correct */
1033 /* work around 'winbind use default domain = yes' */
1035 if ( !strchr_m( pw
->pw_name
, *lp_winbind_separator() ) ) {
1038 /* split the domain and username into 2 strings */
1042 fstr_sprintf(save_username
, "%s%c%s", domain
, *lp_winbind_separator(), pw
->pw_name
);
1045 fstrcpy( save_username
, pw
->pw_name
);
1051 /* setup for lookup of just the username */
1052 /* remember that p and username are overlapping memory */
1055 fstrcpy( strip_username
, p
);
1056 fstrcpy( username
, strip_username
);
1059 /* just lookup a plain username */
1061 pw
= Get_Pwnam_alloc(username
);
1063 /* Create local user if requested. */
1065 if ( !pw
&& create
) {
1066 /* Don't add a machine account. */
1067 if (username
[strlen(username
)-1] == '$')
1070 smb_create_user(NULL
, username
, NULL
);
1071 pw
= Get_Pwnam_alloc(username
);
1074 /* one last check for a valid passwd struct */
1077 fstrcpy( save_username
, pw
->pw_name
);
1082 /***************************************************************************
1083 Make a server_info struct from the info3 returned by a domain logon
1084 ***************************************************************************/
1086 NTSTATUS
make_server_info_info3(TALLOC_CTX
*mem_ctx
,
1087 const char *internal_username
,
1088 const char *sent_nt_username
,
1090 auth_serversupplied_info
**server_info
,
1091 NET_USER_INFO_3
*info3
)
1093 static const char zeros
[16];
1095 NTSTATUS nt_status
= NT_STATUS_OK
;
1096 char *found_username
;
1097 const char *nt_domain
;
1098 const char *nt_username
;
1100 SAM_ACCOUNT
*sam_account
= NULL
;
1108 DOM_SID
*lgroupSIDs
= NULL
;
1110 gid_t
*unix_groups
= NULL
;
1111 NT_USER_TOKEN
*token
;
1113 DOM_SID
*all_group_SIDs
;
1117 Here is where we should check the list of
1118 trusted domains, and verify that the SID
1122 sid_copy(&user_sid
, &info3
->dom_sid
.sid
);
1123 if (!sid_append_rid(&user_sid
, info3
->user_rid
)) {
1124 return NT_STATUS_INVALID_PARAMETER
;
1127 sid_copy(&group_sid
, &info3
->dom_sid
.sid
);
1128 if (!sid_append_rid(&group_sid
, info3
->group_rid
)) {
1129 return NT_STATUS_INVALID_PARAMETER
;
1132 if (!(nt_username
= unistr2_tdup(mem_ctx
, &(info3
->uni_user_name
)))) {
1133 /* If the server didn't give us one, just use the one we sent them */
1134 nt_username
= sent_nt_username
;
1137 if (!(nt_domain
= unistr2_tdup(mem_ctx
, &(info3
->uni_logon_dom
)))) {
1138 /* If the server didn't give us one, just use the one we sent them */
1142 /* try to fill the SAM account.. If getpwnam() fails, then try the
1143 add user script (2.2.x behavior).
1145 We use the _unmapped_ username here in an attempt to provide
1146 consistent username mapping behavior between kerberos and NTLM[SSP]
1147 authentication in domain mode security. I.E. Username mapping should
1148 be applied to the fully qualified username (e.g. DOMAIN\user) and
1149 no just the login name. Yes this mean swe called map_username()
1150 unnecessarily in make_user_info_map() but that is how the current
1151 code is designed. Making the change here is the least disruptive
1154 nt_status
= fill_sam_account(mem_ctx
, nt_domain
, sent_nt_username
,
1155 &found_username
, &uid
, &gid
, &sam_account
);
1157 if (NT_STATUS_EQUAL(nt_status
, NT_STATUS_NO_SUCH_USER
)) {
1158 DEBUG(3,("User %s does not exist, trying to add it\n", internal_username
));
1159 smb_create_user( nt_domain
, sent_nt_username
, NULL
);
1160 nt_status
= fill_sam_account( mem_ctx
, nt_domain
, sent_nt_username
,
1161 &found_username
, &uid
, &gid
, &sam_account
);
1164 /* if we still don't have a valid unix account check for
1165 'map to gues = bad uid' */
1167 if (!NT_STATUS_IS_OK(nt_status
)) {
1168 if ( lp_map_to_guest() == MAP_TO_GUEST_ON_BAD_UID
) {
1169 make_server_info_guest(server_info
);
1170 return NT_STATUS_OK
;
1173 DEBUG(0, ("make_server_info_info3: pdb_init_sam failed!\n"));
1177 if (!pdb_set_nt_username(sam_account
, nt_username
, PDB_CHANGED
)) {
1178 pdb_free_sam(&sam_account
);
1179 return NT_STATUS_NO_MEMORY
;
1182 if (!pdb_set_username(sam_account
, nt_username
, PDB_CHANGED
)) {
1183 pdb_free_sam(&sam_account
);
1184 return NT_STATUS_NO_MEMORY
;
1187 if (!pdb_set_domain(sam_account
, nt_domain
, PDB_CHANGED
)) {
1188 pdb_free_sam(&sam_account
);
1189 return NT_STATUS_NO_MEMORY
;
1192 if (!pdb_set_user_sid(sam_account
, &user_sid
, PDB_CHANGED
)) {
1193 pdb_free_sam(&sam_account
);
1194 return NT_STATUS_UNSUCCESSFUL
;
1197 if (!pdb_set_group_sid(sam_account
, &group_sid
, PDB_CHANGED
)) {
1198 pdb_free_sam(&sam_account
);
1199 return NT_STATUS_UNSUCCESSFUL
;
1202 if (!pdb_set_fullname(sam_account
, unistr2_static(&(info3
->uni_full_name
)),
1204 pdb_free_sam(&sam_account
);
1205 return NT_STATUS_NO_MEMORY
;
1208 if (!pdb_set_logon_script(sam_account
, unistr2_static(&(info3
->uni_logon_script
)), PDB_CHANGED
)) {
1209 pdb_free_sam(&sam_account
);
1210 return NT_STATUS_NO_MEMORY
;
1213 if (!pdb_set_profile_path(sam_account
, unistr2_static(&(info3
->uni_profile_path
)), PDB_CHANGED
)) {
1214 pdb_free_sam(&sam_account
);
1215 return NT_STATUS_NO_MEMORY
;
1218 if (!pdb_set_homedir(sam_account
, unistr2_static(&(info3
->uni_home_dir
)), PDB_CHANGED
)) {
1219 pdb_free_sam(&sam_account
);
1220 return NT_STATUS_NO_MEMORY
;
1223 if (!pdb_set_dir_drive(sam_account
, unistr2_static(&(info3
->uni_dir_drive
)), PDB_CHANGED
)) {
1224 pdb_free_sam(&sam_account
);
1225 return NT_STATUS_NO_MEMORY
;
1228 if (!NT_STATUS_IS_OK(nt_status
= make_server_info(server_info
))) {
1229 DEBUG(4, ("make_server_info failed!\n"));
1230 pdb_free_sam(&sam_account
);
1234 /* save this here to _net_sam_logon() doesn't fail (it assumes a
1235 valid SAM_ACCOUNT) */
1237 (*server_info
)->sam_account
= sam_account
;
1239 (*server_info
)->unix_name
= smb_xstrdup(found_username
);
1241 /* Fill in the unix info we found on the way */
1243 (*server_info
)->sam_fill_level
= SAM_FILL_ALL
;
1244 (*server_info
)->uid
= uid
;
1245 (*server_info
)->gid
= gid
;
1247 /* Store the user group information in the server_info
1248 returned to the caller. */
1250 nt_status
= get_user_groups((*server_info
)->unix_name
,
1251 uid
, gid
, &n_lgroupSIDs
, &lgroupSIDs
, &unix_groups
);
1253 if ( !NT_STATUS_IS_OK(nt_status
) ) {
1254 DEBUG(4,("get_user_groups failed\n"));
1258 (*server_info
)->groups
= unix_groups
;
1259 (*server_info
)->n_groups
= n_lgroupSIDs
;
1261 /* Create a 'combined' list of all SIDs we might want in the SD */
1263 all_group_SIDs
= SMB_MALLOC_ARRAY(DOM_SID
,info3
->num_groups2
+ info3
->num_other_sids
+ n_lgroupSIDs
);
1265 if (!all_group_SIDs
) {
1266 DEBUG(0, ("malloc() failed for DOM_SID list!\n"));
1267 SAFE_FREE(lgroupSIDs
);
1268 free_server_info(server_info
);
1269 return NT_STATUS_NO_MEMORY
;
1272 /* and create (by appending rids) the 'domain' sids */
1274 for (i
= 0; i
< info3
->num_groups2
; i
++) {
1276 sid_copy(&all_group_SIDs
[i
], &(info3
->dom_sid
.sid
));
1278 if (!sid_append_rid(&all_group_SIDs
[i
], info3
->gids
[i
].g_rid
)) {
1280 nt_status
= NT_STATUS_INVALID_PARAMETER
;
1282 DEBUG(3,("could not append additional group rid 0x%x\n",
1283 info3
->gids
[i
].g_rid
));
1285 SAFE_FREE(lgroupSIDs
);
1286 SAFE_FREE(all_group_SIDs
);
1287 free_server_info(server_info
);
1294 /* Copy 'other' sids. We need to do sid filtering here to
1295 prevent possible elevation of privileges. See:
1297 http://www.microsoft.com/windows2000/techinfo/administration/security/sidfilter.asp
1300 for (i
= 0; i
< info3
->num_other_sids
; i
++) {
1301 sid_copy(&all_group_SIDs
[info3
->num_groups2
+ i
],
1302 &info3
->other_sids
[i
].sid
);
1306 /* add local alias sids */
1308 for (i
= 0; i
< n_lgroupSIDs
; i
++) {
1309 sid_copy(&all_group_SIDs
[info3
->num_groups2
+
1310 info3
->num_other_sids
+ i
],
1314 /* Where are the 'global' sids... */
1316 /* can the user be guest? if yes, where is it stored? */
1318 nt_status
= create_nt_user_token(&user_sid
, &group_sid
,
1319 info3
->num_groups2
+ info3
->num_other_sids
+ n_lgroupSIDs
,
1320 all_group_SIDs
, False
, &token
);
1322 if ( !NT_STATUS_IS_OK(nt_status
) ) {
1323 DEBUG(4,("create_nt_user_token failed\n"));
1324 SAFE_FREE(lgroupSIDs
);
1325 SAFE_FREE(all_group_SIDs
);
1326 free_server_info(server_info
);
1330 (*server_info
)->login_server
= unistr2_tdup(mem_ctx
,
1331 &(info3
->uni_logon_srv
));
1333 (*server_info
)->ptok
= token
;
1335 SAFE_FREE(lgroupSIDs
);
1336 SAFE_FREE(all_group_SIDs
);
1338 /* ensure we are never given NULL session keys */
1340 if (memcmp(info3
->user_sess_key
, zeros
, sizeof(zeros
)) == 0) {
1341 (*server_info
)->user_session_key
= data_blob(NULL
, 0);
1343 (*server_info
)->user_session_key
= data_blob(info3
->user_sess_key
, sizeof(info3
->user_sess_key
));
1346 if (memcmp(info3
->lm_sess_key
, zeros
, 8) == 0) {
1347 (*server_info
)->lm_session_key
= data_blob(NULL
, 0);
1349 (*server_info
)->lm_session_key
= data_blob(info3
->lm_sess_key
, sizeof(info3
->lm_sess_key
));
1352 return NT_STATUS_OK
;
1355 /***************************************************************************
1356 Free a user_info struct
1357 ***************************************************************************/
1359 void free_user_info(auth_usersupplied_info
**user_info
)
1361 DEBUG(5,("attempting to free (and zero) a user_info structure\n"));
1362 if (*user_info
!= NULL
) {
1363 if ((*user_info
)->smb_name
.str
) {
1364 DEBUG(10,("structure was created for %s\n", (*user_info
)->smb_name
.str
));
1366 SAFE_FREE((*user_info
)->smb_name
.str
);
1367 SAFE_FREE((*user_info
)->internal_username
.str
);
1368 SAFE_FREE((*user_info
)->client_domain
.str
);
1369 SAFE_FREE((*user_info
)->domain
.str
);
1370 SAFE_FREE((*user_info
)->wksta_name
.str
);
1371 data_blob_free(&(*user_info
)->lm_resp
);
1372 data_blob_free(&(*user_info
)->nt_resp
);
1373 data_blob_clear_free(&(*user_info
)->lm_interactive_pwd
);
1374 data_blob_clear_free(&(*user_info
)->nt_interactive_pwd
);
1375 data_blob_clear_free(&(*user_info
)->plaintext_password
);
1376 ZERO_STRUCT(**user_info
);
1378 SAFE_FREE(*user_info
);
1381 /***************************************************************************
1382 Clear out a server_info struct that has been allocated
1383 ***************************************************************************/
1385 void free_server_info(auth_serversupplied_info
**server_info
)
1387 DEBUG(5,("attempting to free (and zero) a server_info structure\n"));
1388 if (*server_info
!= NULL
) {
1389 pdb_free_sam(&(*server_info
)->sam_account
);
1391 /* call pam_end here, unless we know we are keeping it */
1392 delete_nt_token( &(*server_info
)->ptok
);
1393 SAFE_FREE((*server_info
)->groups
);
1394 SAFE_FREE((*server_info
)->unix_name
);
1395 data_blob_free(&(*server_info
)->lm_session_key
);
1396 data_blob_free(&(*server_info
)->user_session_key
);
1397 ZERO_STRUCT(**server_info
);
1399 SAFE_FREE(*server_info
);
1402 /***************************************************************************
1403 Make an auth_methods struct
1404 ***************************************************************************/
1406 BOOL
make_auth_methods(struct auth_context
*auth_context
, auth_methods
**auth_method
)
1408 if (!auth_context
) {
1409 smb_panic("no auth_context supplied to make_auth_methods()!\n");
1413 smb_panic("make_auth_methods: pointer to auth_method pointer is NULL!\n");
1416 *auth_method
= TALLOC_P(auth_context
->mem_ctx
, auth_methods
);
1417 if (!*auth_method
) {
1418 DEBUG(0,("make_auth_method: malloc failed!\n"));
1421 ZERO_STRUCTP(*auth_method
);
1426 /****************************************************************************
1428 ****************************************************************************/
1430 void delete_nt_token(NT_USER_TOKEN
**pptoken
)
1433 NT_USER_TOKEN
*ptoken
= *pptoken
;
1435 SAFE_FREE( ptoken
->user_sids
);
1436 ZERO_STRUCTP(ptoken
);
1438 SAFE_FREE(*pptoken
);
1441 /****************************************************************************
1442 Duplicate a SID token.
1443 ****************************************************************************/
1445 NT_USER_TOKEN
*dup_nt_token(NT_USER_TOKEN
*ptoken
)
1447 NT_USER_TOKEN
*token
;
1452 if ((token
= SMB_MALLOC_P(NT_USER_TOKEN
)) == NULL
)
1455 ZERO_STRUCTP(token
);
1457 token
->user_sids
= (DOM_SID
*)memdup( ptoken
->user_sids
, sizeof(DOM_SID
) * ptoken
->num_sids
);
1464 token
->num_sids
= ptoken
->num_sids
;
1466 /* copy the privileges; don't consider failure to be critical here */
1468 if ( !se_priv_copy( &token
->privileges
, &ptoken
->privileges
) ) {
1469 DEBUG(0,("dup_nt_token: Failure to copy SE_PRIV!. Continuing with 0 privileges assigned.\n"));
1475 /****************************************************************************
1476 Check for a SID in an NT_USER_TOKEN
1477 ****************************************************************************/
1479 BOOL
nt_token_check_sid ( DOM_SID
*sid
, NT_USER_TOKEN
*token
)
1483 if ( !sid
|| !token
)
1486 for ( i
=0; i
<token
->num_sids
; i
++ ) {
1487 if ( sid_equal( sid
, &token
->user_sids
[i
] ) )
1494 BOOL
nt_token_check_domain_rid( NT_USER_TOKEN
*token
, uint32 rid
)
1498 /* if we are a domain member, the get the domain SID, else for
1499 a DC or standalone server, use our own SID */
1501 if ( lp_server_role() == ROLE_DOMAIN_MEMBER
) {
1502 if ( !secrets_fetch_domain_sid( lp_workgroup(), &domain_sid
) ) {
1503 DEBUG(1,("nt_token_check_domain_rid: Cannot lookup SID for domain [%s]\n",
1509 sid_copy( &domain_sid
, get_global_sam_sid() );
1511 sid_append_rid( &domain_sid
, rid
);
1513 return nt_token_check_sid( &domain_sid
, token
);\
1517 * Verify whether or not given domain is trusted.
1519 * @param domain_name name of the domain to be verified
1520 * @return true if domain is one of the trusted once or
1521 * false if otherwise
1524 BOOL
is_trusted_domain(const char* dom_name
)
1526 DOM_SID trustdom_sid
;
1531 /* no trusted domains for a standalone server */
1533 if ( lp_server_role() == ROLE_STANDALONE
)
1536 /* if we are a DC, then check for a direct trust relationships */
1540 DEBUG (5,("is_trusted_domain: Checking for domain trust with [%s]\n",
1542 ret
= secrets_fetch_trusted_domain_password(dom_name
, &pass
, &trustdom_sid
, &lct
);
1551 /* If winbind is around, ask it */
1553 result
= wb_is_trusted_domain(dom_name
);
1555 if (result
== NSS_STATUS_SUCCESS
) {
1559 if (result
== NSS_STATUS_NOTFOUND
) {
1560 /* winbind could not find the domain */
1564 /* The only other possible result is that winbind is not up
1565 and running. We need to update the trustdom_cache
1568 update_trustdom_cache();
1571 /* now the trustdom cache should be available a DC could still
1572 * have a transitive trust so fall back to the cache of trusted
1573 * domains (like a domain member would use */
1575 if ( trustdom_cache_fetch(dom_name
, &trustdom_sid
) ) {