2 * Unix SMB/CIFS implementation.
3 * RPC Pipe client / server routines
4 * Copyright (C) Andrew Tridgell 1992-1997,
5 * Copyright (C) Luke Kenneth Casson Leighton 1996-1997,
6 * Copyright (C) Paul Ashton 1997,
7 * Copyright (C) Marc Jacobsen 1999,
8 * Copyright (C) Jeremy Allison 2001-2002,
9 * Copyright (C) Jean François Micouleau 1998-2001,
10 * Copyright (C) Anthony Liguori 2002,
11 * Copyright (C) Jim McDonough 2002.
13 * This program is free software; you can redistribute it and/or modify
14 * it under the terms of the GNU General Public License as published by
15 * the Free Software Foundation; either version 2 of the License, or
16 * (at your option) any later version.
18 * This program is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU General Public License for more details.
23 * You should have received a copy of the GNU General Public License
24 * along with this program; if not, write to the Free Software
25 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
29 * This is the implementation of the SAMR code.
35 #define DBGC_CLASS DBGC_RPC_SRV
37 extern DOM_SID global_sid_Builtin;
39 extern rid_name domain_group_rids[];
40 extern rid_name domain_alias_rids[];
41 extern rid_name builtin_alias_rids[];
44 typedef struct _disp_info {
46 uint32 num_user_account;
47 DISP_USER_INFO *disp_user_info;
49 uint32 num_group_account;
50 DISP_GROUP_INFO *disp_group_info;
54 /* for use by the \PIPE\samr policy */
56 uint32 status; /* some sort of flag. best to record it. comes from opnum 0x39 */
65 struct generic_mapping sam_generic_mapping = {GENERIC_RIGHTS_SAM_READ, GENERIC_RIGHTS_SAM_WRITE, GENERIC_RIGHTS_SAM_EXECUTE, GENERIC_RIGHTS_SAM_ALL_ACCESS};
66 struct generic_mapping dom_generic_mapping = {GENERIC_RIGHTS_DOMAIN_READ, GENERIC_RIGHTS_DOMAIN_WRITE, GENERIC_RIGHTS_DOMAIN_EXECUTE, GENERIC_RIGHTS_DOMAIN_ALL_ACCESS};
67 struct generic_mapping usr_generic_mapping = {GENERIC_RIGHTS_USER_READ, GENERIC_RIGHTS_USER_WRITE, GENERIC_RIGHTS_USER_EXECUTE, GENERIC_RIGHTS_USER_ALL_ACCESS};
68 struct generic_mapping grp_generic_mapping = {GENERIC_RIGHTS_GROUP_READ, GENERIC_RIGHTS_GROUP_WRITE, GENERIC_RIGHTS_GROUP_EXECUTE, GENERIC_RIGHTS_GROUP_ALL_ACCESS};
69 struct generic_mapping ali_generic_mapping = {GENERIC_RIGHTS_ALIAS_READ, GENERIC_RIGHTS_ALIAS_WRITE, GENERIC_RIGHTS_ALIAS_EXECUTE, GENERIC_RIGHTS_ALIAS_ALL_ACCESS};
71 static NTSTATUS samr_make_dom_obj_sd(TALLOC_CTX *ctx, SEC_DESC **psd, size_t *sd_size);
73 /*******************************************************************
74 Checks if access to an object should be granted, and returns that
75 level of access for further checks.
76 ********************************************************************/
78 NTSTATUS access_check_samr_object(SEC_DESC *psd, NT_USER_TOKEN *nt_user_token, uint32 des_access,
79 uint32 *acc_granted, const char *debug)
81 NTSTATUS status = NT_STATUS_ACCESS_DENIED;
83 if (!se_access_check(psd, nt_user_token, des_access, acc_granted, &status)) {
84 *acc_granted = des_access;
85 if (geteuid() == sec_initial_uid()) {
86 DEBUG(4,("%s: ACCESS should be DENIED (requested: %#010x)\n",
88 DEBUGADD(4,("but overritten by euid == sec_initial_uid()\n"));
89 status = NT_STATUS_OK;
92 DEBUG(2,("%s: ACCESS DENIED (requested: %#010x)\n",
99 /*******************************************************************
100 Checks if access to a function can be granted
101 ********************************************************************/
103 NTSTATUS access_check_samr_function(uint32 acc_granted, uint32 acc_required, const char *debug)
105 DEBUG(5,("%s: access check ((granted: %#010x; required: %#010x)\n",
106 debug, acc_granted, acc_required));
107 if ((acc_granted & acc_required) != acc_required) {
108 if (geteuid() == sec_initial_uid()) {
109 DEBUG(4,("%s: ACCESS should be DENIED (granted: %#010x; required: %#010x)\n",
110 debug, acc_granted, acc_required));
111 DEBUGADD(4,("but overwritten by euid == 0\n"));
114 DEBUG(2,("%s: ACCESS DENIED (granted: %#010x; required: %#010x)\n",
115 debug, acc_granted, acc_required));
116 return NT_STATUS_ACCESS_DENIED;
122 /*******************************************************************
123 Create a samr_info struct.
124 ********************************************************************/
126 static struct samr_info *get_samr_info_by_sid(DOM_SID *psid)
128 struct samr_info *info;
133 sid_to_string(sid_str, psid);
135 fstrcpy(sid_str,"(NULL)");
138 mem_ctx = talloc_init("samr_info for domain sid %s", sid_str);
140 if ((info = (struct samr_info *)talloc(mem_ctx, sizeof(struct samr_info))) == NULL)
144 DEBUG(10,("get_samr_info_by_sid: created new info for sid %s\n", sid_str));
146 sid_copy( &info->sid, psid);
148 DEBUG(10,("get_samr_info_by_sid: created new info for NULL sid.\n"));
150 info->mem_ctx = mem_ctx;
155 /*******************************************************************
156 Function to free the per handle data.
157 ********************************************************************/
158 static void free_samr_users(struct samr_info *info)
162 if (info->disp_info.user_dbloaded){
163 for (i=0; i<info->disp_info.num_user_account; i++) {
164 /* Not really a free, actually a 'clear' */
165 pdb_free_sam(&info->disp_info.disp_user_info[i].sam);
168 info->disp_info.user_dbloaded=False;
169 info->disp_info.num_user_account=0;
173 /*******************************************************************
174 Function to free the per handle data.
175 ********************************************************************/
176 static void free_samr_db(struct samr_info *info)
178 /* Groups are talloced */
180 free_samr_users(info);
182 info->disp_info.group_dbloaded=False;
183 info->disp_info.num_group_account=0;
187 static void free_samr_info(void *ptr)
189 struct samr_info *info=(struct samr_info *) ptr;
192 talloc_destroy(info->mem_ctx);
195 /*******************************************************************
196 Ensure password info is never given out. Paranioa... JRA.
197 ********************************************************************/
199 static void samr_clear_sam_passwd(SAM_ACCOUNT *sam_pass)
205 /* These now zero out the old password */
207 pdb_set_lanman_passwd(sam_pass, NULL, PDB_DEFAULT);
208 pdb_set_nt_passwd(sam_pass, NULL, PDB_DEFAULT);
212 static NTSTATUS load_sampwd_entries(struct samr_info *info, uint16 acb_mask, BOOL all_machines)
214 SAM_ACCOUNT *pwd = NULL;
215 DISP_USER_INFO *pwd_array = NULL;
216 NTSTATUS nt_status = NT_STATUS_OK;
217 TALLOC_CTX *mem_ctx = info->mem_ctx;
219 DEBUG(10,("load_sampwd_entries\n"));
221 /* if the snapshoot is already loaded, return */
222 if ((info->disp_info.user_dbloaded==True)
223 && (info->acb_mask == acb_mask)
224 && (info->all_machines == all_machines)) {
225 DEBUG(10,("load_sampwd_entries: already in memory\n"));
229 free_samr_users(info);
231 if (!pdb_setsampwent(False)) {
232 DEBUG(0, ("load_sampwd_entries: Unable to open passdb.\n"));
233 return NT_STATUS_ACCESS_DENIED;
236 for (; (NT_STATUS_IS_OK(nt_status = pdb_init_sam_talloc(mem_ctx, &pwd)))
237 && pdb_getsampwent(pwd) == True; pwd=NULL) {
240 if (!((pdb_get_acct_ctrl(pwd) & ACB_WSTRUST)
241 || (pdb_get_acct_ctrl(pwd) & ACB_SVRTRUST))) {
242 DEBUG(5,("load_sampwd_entries: '%s' is not a machine account - ACB: %x - skipping\n", pdb_get_username(pwd), acb_mask));
247 if (acb_mask != 0 && !(pdb_get_acct_ctrl(pwd) & acb_mask)) {
249 DEBUG(5,(" acb_mask %x reject\n", acb_mask));
254 /* Realloc some memory for the array of ptr to the SAM_ACCOUNT structs */
255 if (info->disp_info.num_user_account % MAX_SAM_ENTRIES == 0) {
257 DEBUG(10,("load_sampwd_entries: allocating more memory\n"));
258 pwd_array=(DISP_USER_INFO *)talloc_realloc(mem_ctx, info->disp_info.disp_user_info,
259 (info->disp_info.num_user_account+MAX_SAM_ENTRIES)*sizeof(DISP_USER_INFO));
262 return NT_STATUS_NO_MEMORY;
264 info->disp_info.disp_user_info=pwd_array;
267 /* link the SAM_ACCOUNT to the array */
268 info->disp_info.disp_user_info[info->disp_info.num_user_account].sam=pwd;
270 DEBUG(10,("load_sampwd_entries: entry: %d\n", info->disp_info.num_user_account));
272 info->disp_info.num_user_account++;
277 /* the snapshoot is in memory, we're ready to enumerate fast */
279 info->acb_mask = acb_mask;
280 info->all_machines = all_machines;
281 info->disp_info.user_dbloaded=True;
283 DEBUG(10,("load_sampwd_entries: done\n"));
288 static NTSTATUS load_group_domain_entries(struct samr_info *info, DOM_SID *sid)
291 DISP_GROUP_INFO *grp_array = NULL;
292 uint32 group_entries = 0;
294 TALLOC_CTX *mem_ctx = info->mem_ctx;
296 DEBUG(10,("load_group_domain_entries\n"));
298 /* if the snapshoot is already loaded, return */
299 if (info->disp_info.group_dbloaded==True) {
300 DEBUG(10,("load_group_domain_entries: already in memory\n"));
304 if (!pdb_enum_group_mapping(SID_NAME_DOM_GRP, &map, (int *)&group_entries, ENUM_ONLY_MAPPED, MAPPING_WITHOUT_PRIV)) {
305 DEBUG(1, ("load_group_domain_entries: pdb_enum_group_mapping() failed!\n"));
306 return NT_STATUS_NO_MEMORY;
309 info->disp_info.num_group_account=group_entries;
311 grp_array=(DISP_GROUP_INFO *)talloc(mem_ctx, info->disp_info.num_group_account*sizeof(DISP_GROUP_INFO));
313 if (group_entries!=0 && grp_array==NULL) {
314 DEBUG(1, ("load_group_domain_entries: talloc() failed for grp_array!\n"));
316 return NT_STATUS_NO_MEMORY;
319 info->disp_info.disp_group_info=grp_array;
321 for (i=0; i<group_entries; i++) {
323 grp_array[i].grp=(DOMAIN_GRP *)talloc(mem_ctx, sizeof(DOMAIN_GRP));
325 fstrcpy(grp_array[i].grp->name, map[i].nt_name);
326 fstrcpy(grp_array[i].grp->comment, map[i].comment);
327 sid_split_rid(&map[i].sid, &grp_array[i].grp->rid);
328 grp_array[i].grp->attr=SID_NAME_DOM_GRP;
333 /* the snapshoot is in memory, we're ready to enumerate fast */
335 info->disp_info.group_dbloaded=True;
337 DEBUG(10,("load_group_domain_entries: done\n"));
343 /*******************************************************************
345 ********************************************************************/
347 NTSTATUS _samr_close_hnd(pipes_struct *p, SAMR_Q_CLOSE_HND *q_u, SAMR_R_CLOSE_HND *r_u)
349 r_u->status = NT_STATUS_OK;
351 /* close the policy handle */
352 if (!close_policy_hnd(p, &q_u->pol))
353 return NT_STATUS_OBJECT_NAME_INVALID;
355 DEBUG(5,("samr_reply_close_hnd: %d\n", __LINE__));
360 /*******************************************************************
361 samr_reply_open_domain
362 ********************************************************************/
364 NTSTATUS _samr_open_domain(pipes_struct *p, SAMR_Q_OPEN_DOMAIN *q_u, SAMR_R_OPEN_DOMAIN *r_u)
366 struct samr_info *info;
367 SEC_DESC *psd = NULL;
369 uint32 des_access = q_u->flags;
373 r_u->status = NT_STATUS_OK;
375 /* find the connection policy handle. */
376 if (!find_policy_by_hnd(p, &q_u->pol, (void**)&info))
377 return NT_STATUS_INVALID_HANDLE;
379 if (!NT_STATUS_IS_OK(status = access_check_samr_function(info->acc_granted, SA_RIGHT_SAM_OPEN_DOMAIN,"_samr_open_domain"))) {
383 /*check if access can be granted as requested by client. */
384 samr_make_dom_obj_sd(p->mem_ctx, &psd, &sd_size);
385 se_map_generic(&des_access,&dom_generic_mapping);
387 if (!NT_STATUS_IS_OK(status =
388 access_check_samr_object(psd, p->pipe_user.nt_user_token,
389 des_access, &acc_granted, "_samr_open_domain"))) {
393 /* associate the domain SID with the (unique) handle. */
394 if ((info = get_samr_info_by_sid(&q_u->dom_sid.sid))==NULL)
395 return NT_STATUS_NO_MEMORY;
396 info->acc_granted = acc_granted;
398 /* get a (unique) handle. open a policy on it. */
399 if (!create_policy_hnd(p, &r_u->domain_pol, free_samr_info, (void *)info))
400 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
402 DEBUG(5,("samr_open_domain: %d\n", __LINE__));
407 /*******************************************************************
408 _samr_get_usrdom_pwinfo
409 ********************************************************************/
411 NTSTATUS _samr_get_usrdom_pwinfo(pipes_struct *p, SAMR_Q_GET_USRDOM_PWINFO *q_u, SAMR_R_GET_USRDOM_PWINFO *r_u)
413 struct samr_info *info = NULL;
415 r_u->status = NT_STATUS_OK;
417 /* find the policy handle. open a policy on it. */
418 if (!find_policy_by_hnd(p, &q_u->user_pol, (void **)&info))
419 return NT_STATUS_INVALID_HANDLE;
421 if (!sid_check_is_in_our_domain(&info->sid))
422 return NT_STATUS_OBJECT_TYPE_MISMATCH;
424 init_samr_r_get_usrdom_pwinfo(r_u, NT_STATUS_OK);
426 DEBUG(5,("_samr_get_usrdom_pwinfo: %d\n", __LINE__));
429 * NT sometimes return NT_STATUS_ACCESS_DENIED
430 * I don't know yet why.
436 /*******************************************************************
438 ********************************************************************/
440 static NTSTATUS samr_make_dom_obj_sd(TALLOC_CTX *ctx, SEC_DESC **psd, size_t *sd_size)
442 extern DOM_SID global_sid_World;
451 sid_copy(&adm_sid, &global_sid_Builtin);
452 sid_append_rid(&adm_sid, BUILTIN_ALIAS_RID_ADMINS);
454 sid_copy(&act_sid, &global_sid_Builtin);
455 sid_append_rid(&act_sid, BUILTIN_ALIAS_RID_ACCOUNT_OPS);
457 /*basic access for every one*/
458 init_sec_access(&mask, GENERIC_RIGHTS_DOMAIN_EXECUTE | GENERIC_RIGHTS_DOMAIN_READ);
459 init_sec_ace(&ace[0], &global_sid_World, SEC_ACE_TYPE_ACCESS_ALLOWED, mask, 0);
461 /*full access for builtin aliases Administrators and Account Operators*/
462 init_sec_access(&mask, GENERIC_RIGHTS_DOMAIN_ALL_ACCESS);
463 init_sec_ace(&ace[1], &adm_sid, SEC_ACE_TYPE_ACCESS_ALLOWED, mask, 0);
464 init_sec_ace(&ace[2], &act_sid, SEC_ACE_TYPE_ACCESS_ALLOWED, mask, 0);
466 if ((psa = make_sec_acl(ctx, NT4_ACL_REVISION, 3, ace)) == NULL)
467 return NT_STATUS_NO_MEMORY;
469 if ((*psd = make_sec_desc(ctx, SEC_DESC_REVISION, NULL, NULL, NULL, psa, sd_size)) == NULL)
470 return NT_STATUS_NO_MEMORY;
475 /*******************************************************************
477 ********************************************************************/
479 static NTSTATUS samr_make_usr_obj_sd(TALLOC_CTX *ctx, SEC_DESC **psd, size_t *sd_size, DOM_SID *usr_sid)
481 extern DOM_SID global_sid_World;
490 sid_copy(&adm_sid, &global_sid_Builtin);
491 sid_append_rid(&adm_sid, BUILTIN_ALIAS_RID_ADMINS);
493 sid_copy(&act_sid, &global_sid_Builtin);
494 sid_append_rid(&act_sid, BUILTIN_ALIAS_RID_ACCOUNT_OPS);
496 /*basic access for every one*/
497 init_sec_access(&mask, GENERIC_RIGHTS_USER_EXECUTE | GENERIC_RIGHTS_USER_READ);
498 init_sec_ace(&ace[0], &global_sid_World, SEC_ACE_TYPE_ACCESS_ALLOWED, mask, 0);
500 /*full access for builtin aliases Administrators and Account Operators*/
501 init_sec_access(&mask, GENERIC_RIGHTS_USER_ALL_ACCESS);
502 init_sec_ace(&ace[1], &adm_sid, SEC_ACE_TYPE_ACCESS_ALLOWED, mask, 0);
503 init_sec_ace(&ace[2], &act_sid, SEC_ACE_TYPE_ACCESS_ALLOWED, mask, 0);
505 /*extended access for the user*/
506 init_sec_access(&mask,READ_CONTROL_ACCESS | SA_RIGHT_USER_CHANGE_PASSWORD | SA_RIGHT_USER_SET_LOC_COM);
507 init_sec_ace(&ace[3], usr_sid, SEC_ACE_TYPE_ACCESS_ALLOWED, mask, 0);
509 if ((psa = make_sec_acl(ctx, NT4_ACL_REVISION, 4, ace)) == NULL)
510 return NT_STATUS_NO_MEMORY;
512 if ((*psd = make_sec_desc(ctx, SEC_DESC_REVISION, NULL, NULL, NULL, psa, sd_size)) == NULL)
513 return NT_STATUS_NO_MEMORY;
518 /*******************************************************************
520 ********************************************************************/
522 static NTSTATUS samr_make_grp_obj_sd(TALLOC_CTX *ctx, SEC_DESC **psd, size_t *sd_size)
524 extern DOM_SID global_sid_World;
533 sid_copy(&adm_sid, &global_sid_Builtin);
534 sid_append_rid(&adm_sid, BUILTIN_ALIAS_RID_ADMINS);
536 sid_copy(&act_sid, &global_sid_Builtin);
537 sid_append_rid(&act_sid, BUILTIN_ALIAS_RID_ACCOUNT_OPS);
539 /*basic access for every one*/
540 init_sec_access(&mask, GENERIC_RIGHTS_GROUP_EXECUTE | GENERIC_RIGHTS_GROUP_READ);
541 init_sec_ace(&ace[0], &global_sid_World, SEC_ACE_TYPE_ACCESS_ALLOWED, mask, 0);
543 /*full access for builtin aliases Administrators and Account Operators*/
544 init_sec_access(&mask, GENERIC_RIGHTS_GROUP_ALL_ACCESS);
545 init_sec_ace(&ace[1], &adm_sid, SEC_ACE_TYPE_ACCESS_ALLOWED, mask, 0);
546 init_sec_ace(&ace[2], &act_sid, SEC_ACE_TYPE_ACCESS_ALLOWED, mask, 0);
548 if ((psa = make_sec_acl(ctx, NT4_ACL_REVISION, 3, ace)) == NULL)
549 return NT_STATUS_NO_MEMORY;
551 if ((*psd = make_sec_desc(ctx, SEC_DESC_REVISION, NULL, NULL, NULL, psa, sd_size)) == NULL)
552 return NT_STATUS_NO_MEMORY;
557 /*******************************************************************
559 ********************************************************************/
561 static NTSTATUS samr_make_ali_obj_sd(TALLOC_CTX *ctx, SEC_DESC **psd, size_t *sd_size)
563 extern DOM_SID global_sid_World;
572 sid_copy(&adm_sid, &global_sid_Builtin);
573 sid_append_rid(&adm_sid, BUILTIN_ALIAS_RID_ADMINS);
575 sid_copy(&act_sid, &global_sid_Builtin);
576 sid_append_rid(&act_sid, BUILTIN_ALIAS_RID_ACCOUNT_OPS);
578 /*basic access for every one*/
579 init_sec_access(&mask, GENERIC_RIGHTS_ALIAS_EXECUTE | GENERIC_RIGHTS_ALIAS_READ);
580 init_sec_ace(&ace[0], &global_sid_World, SEC_ACE_TYPE_ACCESS_ALLOWED, mask, 0);
582 /*full access for builtin aliases Administrators and Account Operators*/
583 init_sec_access(&mask, GENERIC_RIGHTS_ALIAS_ALL_ACCESS);
584 init_sec_ace(&ace[1], &adm_sid, SEC_ACE_TYPE_ACCESS_ALLOWED, mask, 0);
585 init_sec_ace(&ace[2], &act_sid, SEC_ACE_TYPE_ACCESS_ALLOWED, mask, 0);
587 if ((psa = make_sec_acl(ctx, NT4_ACL_REVISION, 3, ace)) == NULL)
588 return NT_STATUS_NO_MEMORY;
590 if ((*psd = make_sec_desc(ctx, SEC_DESC_REVISION, NULL, NULL, NULL, psa, sd_size)) == NULL)
591 return NT_STATUS_NO_MEMORY;
596 static BOOL get_lsa_policy_samr_sid(pipes_struct *p, POLICY_HND *pol, DOM_SID *sid, uint32 *acc_granted)
598 struct samr_info *info = NULL;
600 /* find the policy handle. open a policy on it. */
601 if (!find_policy_by_hnd(p, pol, (void **)&info))
608 *acc_granted = info->acc_granted;
612 /*******************************************************************
614 ********************************************************************/
616 NTSTATUS _samr_set_sec_obj(pipes_struct *p, SAMR_Q_SET_SEC_OBJ *q_u, SAMR_R_SET_SEC_OBJ *r_u)
618 DEBUG(0,("_samr_set_sec_obj: Not yet implemented!\n"));
619 return NT_STATUS_NOT_IMPLEMENTED;
623 /*******************************************************************
625 ********************************************************************/
627 NTSTATUS _samr_query_sec_obj(pipes_struct *p, SAMR_Q_QUERY_SEC_OBJ *q_u, SAMR_R_QUERY_SEC_OBJ *r_u)
631 SEC_DESC * psd = NULL;
635 r_u->status = NT_STATUS_OK;
638 if (!get_lsa_policy_samr_sid(p, &q_u->user_pol, &pol_sid, &acc_granted))
639 return NT_STATUS_INVALID_HANDLE;
643 DEBUG(10,("_samr_query_sec_obj: querying security on SID: %s\n", sid_to_string(str_sid, &pol_sid)));
645 /* Check what typ of SID is beeing queried (e.g Domain SID, User SID, Group SID) */
647 /* To query the security of the SAM it self an invalid SID with S-0-0 is passed to this function */
648 if (pol_sid.sid_rev_num == 0)
650 DEBUG(5,("_samr_query_sec_obj: querying security on SAM\n"));
651 r_u->status = samr_make_sam_obj_sd(p->mem_ctx, &psd, &sd_size);
653 else if (sid_equal(&pol_sid,get_global_sam_sid())) /* check if it is our domain SID */
656 DEBUG(5,("_samr_query_sec_obj: querying security on Domain with SID: %s\n", sid_to_string(str_sid, &pol_sid)));
657 r_u->status = samr_make_dom_obj_sd(p->mem_ctx, &psd, &sd_size);
659 else if (sid_equal(&pol_sid,&global_sid_Builtin)) /* check if it is the Builtin Domain */
661 /* TODO: Builtin probably needs a different SD with restricted write access*/
662 DEBUG(5,("_samr_query_sec_obj: querying security on Builtin Domain with SID: %s\n", sid_to_string(str_sid, &pol_sid)));
663 r_u->status = samr_make_dom_obj_sd(p->mem_ctx, &psd, &sd_size);
665 else if (sid_check_is_in_our_domain(&pol_sid) ||
666 sid_check_is_in_builtin(&pol_sid))
668 /* TODO: different SDs have to be generated for aliases groups and users.
669 Currently all three get a default user SD */
670 DEBUG(10,("_samr_query_sec_obj: querying security on Object with SID: %s\n", sid_to_string(str_sid, &pol_sid)));
671 r_u->status = samr_make_usr_obj_sd(p->mem_ctx, &psd,&sd_size, &pol_sid);
673 else return NT_STATUS_OBJECT_TYPE_MISMATCH;
675 if ((r_u->buf = make_sec_desc_buf(p->mem_ctx, sd_size, psd)) == NULL)
676 return NT_STATUS_NO_MEMORY;
678 if (NT_STATUS_IS_OK(r_u->status))
684 /*******************************************************************
685 makes a SAM_ENTRY / UNISTR2* structure from a user list.
686 ********************************************************************/
688 static NTSTATUS make_user_sam_entry_list(TALLOC_CTX *ctx, SAM_ENTRY **sam_pp, UNISTR2 **uni_name_pp,
689 uint32 num_entries, uint32 start_idx, DISP_USER_INFO *disp_user_info,
695 SAM_ACCOUNT *pwd = NULL;
696 UNISTR2 uni_temp_name;
697 const char *temp_name;
698 const DOM_SID *user_sid;
700 fstring user_sid_string;
701 fstring domain_sid_string;
706 if (num_entries == 0)
709 sam = (SAM_ENTRY *)talloc_zero(ctx, sizeof(SAM_ENTRY)*num_entries);
711 uni_name = (UNISTR2 *)talloc_zero(ctx, sizeof(UNISTR2)*num_entries);
713 if (sam == NULL || uni_name == NULL) {
714 DEBUG(0, ("make_user_sam_entry_list: talloc_zero failed!\n"));
715 return NT_STATUS_NO_MEMORY;
718 for (i = 0; i < num_entries; i++) {
719 pwd = disp_user_info[i+start_idx].sam;
720 temp_name = pdb_get_username(pwd);
721 init_unistr2(&uni_temp_name, temp_name, strlen(temp_name)+1);
722 user_sid = pdb_get_user_sid(pwd);
724 if (!sid_peek_check_rid(domain_sid, user_sid, &user_rid)) {
725 DEBUG(0, ("make_user_sam_entry_list: User %s has SID %s, which conflicts with "
726 "the domain sid %s. Failing operation.\n",
728 sid_to_string(user_sid_string, user_sid),
729 sid_to_string(domain_sid_string, domain_sid)));
730 return NT_STATUS_UNSUCCESSFUL;
733 init_sam_entry(&sam[i], uni_temp_name.uni_str_len, user_rid);
734 copy_unistr2(&uni_name[i], &uni_temp_name);
738 *uni_name_pp = uni_name;
742 /*******************************************************************
743 samr_reply_enum_dom_users
744 ********************************************************************/
746 NTSTATUS _samr_enum_dom_users(pipes_struct *p, SAMR_Q_ENUM_DOM_USERS *q_u,
747 SAMR_R_ENUM_DOM_USERS *r_u)
749 struct samr_info *info = NULL;
750 uint32 struct_size=0x20; /* W2K always reply that, client doesn't care */
752 uint32 enum_context=q_u->start_idx;
753 uint32 max_size=q_u->max_size;
755 enum remote_arch_types ra_type = get_remote_arch();
756 int max_sam_entries = (ra_type == RA_WIN95) ? MAX_SAM_ENTRIES_W95 : MAX_SAM_ENTRIES_W2K;
757 uint32 max_entries = max_sam_entries;
760 r_u->status = NT_STATUS_OK;
762 /* find the policy handle. open a policy on it. */
763 if (!find_policy_by_hnd(p, &q_u->pol, (void **)&info))
764 return NT_STATUS_INVALID_HANDLE;
766 domain_sid = info->sid;
768 if (!NT_STATUS_IS_OK(r_u->status = access_check_samr_function(info->acc_granted,
769 SA_RIGHT_DOMAIN_ENUM_ACCOUNTS,
770 "_samr_enum_dom_users"))) {
774 DEBUG(5,("_samr_enum_dom_users: %d\n", __LINE__));
777 r_u->status=load_sampwd_entries(info, q_u->acb_mask, False);
780 if (!NT_STATUS_IS_OK(r_u->status))
783 num_account = info->disp_info.num_user_account;
785 if (enum_context > num_account) {
786 DEBUG(5, ("_samr_enum_dom_users: enumeration handle over total entries\n"));
790 /* verify we won't overflow */
791 if (max_entries > num_account-enum_context) {
792 max_entries = num_account-enum_context;
793 DEBUG(5, ("_samr_enum_dom_users: only %d entries to return\n", max_entries));
796 /* calculate the size and limit on the number of entries we will return */
797 temp_size=max_entries*struct_size;
799 if (temp_size>max_size) {
800 max_entries=MIN((max_size/struct_size),max_entries);;
801 DEBUG(5, ("_samr_enum_dom_users: buffer size limits to only %d entries\n", max_entries));
805 * Note from JRA. total_entries is not being used here. Currently if there is a
806 * large user base then it looks like NT will enumerate until get_sampwd_entries
807 * returns False due to num_entries being zero. This will cause an access denied
808 * return. I don't think this is right and needs further investigation. Note that
809 * this is also the same in the TNG code (I don't think that has been tested with
810 * a very large user list as MAX_SAM_ENTRIES is set to 600).
812 * I also think that one of the 'num_entries' return parameters is probably
813 * the "max entries" parameter - but in the TNG code they're all currently set to the same
814 * value (again I think this is wrong).
817 r_u->status = make_user_sam_entry_list(p->mem_ctx, &r_u->sam, &r_u->uni_acct_name,
818 max_entries, enum_context,
819 info->disp_info.disp_user_info,
822 if (!NT_STATUS_IS_OK(r_u->status))
825 if (enum_context+max_entries < num_account)
826 r_u->status = STATUS_MORE_ENTRIES;
828 DEBUG(5, ("_samr_enum_dom_users: %d\n", __LINE__));
830 init_samr_r_enum_dom_users(r_u, q_u->start_idx + max_entries, max_entries);
832 DEBUG(5,("_samr_enum_dom_users: %d\n", __LINE__));
837 /*******************************************************************
838 makes a SAM_ENTRY / UNISTR2* structure from a group list.
839 ********************************************************************/
841 static void make_group_sam_entry_list(TALLOC_CTX *ctx, SAM_ENTRY **sam_pp, UNISTR2 **uni_name_pp,
842 uint32 num_sam_entries, DOMAIN_GRP *grp)
851 if (num_sam_entries == 0)
854 sam = (SAM_ENTRY *)talloc_zero(ctx, sizeof(SAM_ENTRY)*num_sam_entries);
856 uni_name = (UNISTR2 *)talloc_zero(ctx, sizeof(UNISTR2)*num_sam_entries);
858 if (sam == NULL || uni_name == NULL) {
859 DEBUG(0, ("NULL pointers in SAMR_R_QUERY_DISPINFO\n"));
863 for (i = 0; i < num_sam_entries; i++) {
865 * JRA. I think this should include the null. TNG does not.
867 int len = strlen(grp[i].name)+1;
869 init_sam_entry(&sam[i], len, grp[i].rid);
870 init_unistr2(&uni_name[i], grp[i].name, len);
874 *uni_name_pp = uni_name;
877 /*******************************************************************
878 Get the group entries - similar to get_sampwd_entries().
879 ********************************************************************/
881 static NTSTATUS get_group_alias_entries(TALLOC_CTX *ctx, DOMAIN_GRP **d_grp, DOM_SID *sid, uint32 start_idx,
882 uint32 *p_num_entries, uint32 max_entries)
885 uint32 num_entries = 0;
888 GROUP_MAP *map = NULL;
890 sid_to_string(sid_str, sid);
891 DEBUG(5, ("get_group_alias_entries: enumerating aliases on SID: %s\n", sid_str));
895 /* well-known aliases */
896 if (sid_equal(sid, &global_sid_Builtin) && !lp_hide_local_users()) {
898 pdb_enum_group_mapping(SID_NAME_WKN_GRP, &map, (int *)&num_entries, ENUM_ONLY_MAPPED, MAPPING_WITHOUT_PRIV);
900 if (num_entries != 0) {
901 *d_grp=(DOMAIN_GRP *)talloc_zero(ctx, num_entries*sizeof(DOMAIN_GRP));
903 return NT_STATUS_NO_MEMORY;
905 for(i=0; i<num_entries && i<max_entries; i++) {
906 fstrcpy((*d_grp)[i].name, map[i+start_idx].nt_name);
907 sid_split_rid(&map[i+start_idx].sid, &(*d_grp)[i].rid);
913 } else if (sid_equal(sid, get_global_sam_sid()) && !lp_hide_local_users()) {
914 struct sys_grent *glist;
915 struct sys_grent *grp;
917 gid_t winbind_gid_low, winbind_gid_high;
918 BOOL winbind_groups_exist = lp_winbind_gid(&winbind_gid_low, &winbind_gid_high);
921 /* we return the UNIX groups here. This seems to be the right */
922 /* thing to do, since NT member servers return their local */
923 /* groups in the same situation. */
925 /* use getgrent_list() to retrieve the list of groups to avoid
926 * problems with getgrent possible infinite loop by internal
927 * libc grent structures overwrites by called functions */
928 grp = glist = getgrent_list();
930 return NT_STATUS_NO_MEMORY;
932 for (; (num_entries < max_entries) && (grp != NULL); grp = grp->next) {
935 if(!pdb_getgrgid(&smap, grp->gr_gid, MAPPING_WITHOUT_PRIV))
938 if (smap.sid_name_use!=SID_NAME_ALIAS) {
942 sid_split_rid(&smap.sid, &trid);
944 if (!sid_equal(sid, &smap.sid))
947 /* Don't return winbind groups as they are not local! */
948 if (winbind_groups_exist && (grp->gr_gid >= winbind_gid_low)&&(grp->gr_gid <= winbind_gid_high)) {
949 DEBUG(10,("get_group_alias_entries: not returing %s, not local.\n", smap.nt_name ));
953 /* Don't return user private groups... */
955 if ((pw = Get_Pwnam(smap.nt_name)) != 0) {
956 DEBUG(10,("get_group_alias_entries: not returing %s, clashes with user.\n", smap.nt_name ));
960 for( i = 0; i < num_entries; i++)
961 if ( (*d_grp)[i].rid == trid )
964 if ( i < num_entries ) {
965 continue; /* rid was there, dup! */
968 /* JRA - added this for large group db enumeration... */
971 /* skip the requested number of entries.
972 not very efficient, but hey...
978 *d_grp=talloc_realloc(ctx,*d_grp, (num_entries+1)*sizeof(DOMAIN_GRP));
981 return NT_STATUS_NO_MEMORY;
984 fstrcpy((*d_grp)[num_entries].name, smap.nt_name);
985 (*d_grp)[num_entries].rid = trid;
987 DEBUG(10,("get_group_alias_entries: added entry %d, rid:%d\n", num_entries, trid));
993 *p_num_entries = num_entries;
995 DEBUG(10,("get_group_alias_entries: returning %d entries\n", *p_num_entries));
997 if (num_entries >= max_entries)
998 return STATUS_MORE_ENTRIES;
1002 /*******************************************************************
1003 Get the group entries - similar to get_sampwd_entries().
1004 ********************************************************************/
1006 static NTSTATUS get_group_domain_entries(TALLOC_CTX *ctx, DOMAIN_GRP **d_grp, DOM_SID *sid, uint32 start_idx,
1007 uint32 *p_num_entries, uint32 max_entries)
1009 GROUP_MAP *map=NULL;
1011 uint32 group_entries = 0;
1012 uint32 num_entries = 0;
1016 pdb_enum_group_mapping(SID_NAME_DOM_GRP, &map, (int *)&group_entries, ENUM_ONLY_MAPPED, MAPPING_WITHOUT_PRIV);
1018 num_entries=group_entries-start_idx;
1020 /* limit the number of entries */
1021 if (num_entries>max_entries) {
1022 DEBUG(5,("Limiting to %d entries\n", max_entries));
1023 num_entries=max_entries;
1026 *d_grp=(DOMAIN_GRP *)talloc_zero(ctx, num_entries*sizeof(DOMAIN_GRP));
1027 if (num_entries!=0 && *d_grp==NULL){
1029 return NT_STATUS_NO_MEMORY;
1032 for (i=0; i<num_entries; i++) {
1033 fstrcpy((*d_grp)[i].name, map[i+start_idx].nt_name);
1034 fstrcpy((*d_grp)[i].comment, map[i+start_idx].comment);
1035 sid_split_rid(&map[i+start_idx].sid, &(*d_grp)[i].rid);
1036 (*d_grp)[i].attr=SID_NAME_DOM_GRP;
1041 *p_num_entries = num_entries;
1043 return NT_STATUS_OK;
1046 /*******************************************************************
1047 samr_reply_enum_dom_groups
1048 ********************************************************************/
1050 NTSTATUS _samr_enum_dom_groups(pipes_struct *p, SAMR_Q_ENUM_DOM_GROUPS *q_u, SAMR_R_ENUM_DOM_GROUPS *r_u)
1052 DOMAIN_GRP *grp=NULL;
1057 r_u->status = NT_STATUS_OK;
1059 if (!get_lsa_policy_samr_sid(p, &q_u->pol, &sid, &acc_granted))
1060 return NT_STATUS_INVALID_HANDLE;
1062 if (!NT_STATUS_IS_OK(r_u->status = access_check_samr_function(acc_granted, SA_RIGHT_DOMAIN_ENUM_ACCOUNTS, "_samr_enum_dom_groups"))) {
1066 DEBUG(5,("samr_reply_enum_dom_groups: %d\n", __LINE__));
1068 /* the domain group array is being allocated in the function below */
1069 if (!NT_STATUS_IS_OK(r_u->status = get_group_domain_entries(p->mem_ctx, &grp, &sid, q_u->start_idx, &num_entries, MAX_SAM_ENTRIES))) {
1073 make_group_sam_entry_list(p->mem_ctx, &r_u->sam, &r_u->uni_grp_name, num_entries, grp);
1075 init_samr_r_enum_dom_groups(r_u, q_u->start_idx, num_entries);
1077 DEBUG(5,("samr_enum_dom_groups: %d\n", __LINE__));
1083 /*******************************************************************
1084 samr_reply_enum_dom_aliases
1085 ********************************************************************/
1087 NTSTATUS _samr_enum_dom_aliases(pipes_struct *p, SAMR_Q_ENUM_DOM_ALIASES *q_u, SAMR_R_ENUM_DOM_ALIASES *r_u)
1089 DOMAIN_GRP *grp=NULL;
1090 uint32 num_entries = 0;
1096 r_u->status = NT_STATUS_OK;
1098 if (!get_lsa_policy_samr_sid(p, &q_u->pol, &sid, &acc_granted))
1099 return NT_STATUS_INVALID_HANDLE;
1101 if (!NT_STATUS_IS_OK(r_u->status = access_check_samr_function(acc_granted, SA_RIGHT_DOMAIN_ENUM_ACCOUNTS, "_samr_enum_dom_aliases"))) {
1105 sid_to_string(sid_str, &sid);
1106 DEBUG(5,("samr_reply_enum_dom_aliases: sid %s\n", sid_str));
1108 status = get_group_alias_entries(p->mem_ctx, &grp, &sid, q_u->start_idx,
1109 &num_entries, MAX_SAM_ENTRIES);
1110 if (NT_STATUS_IS_ERR(status)) return status;
1112 make_group_sam_entry_list(p->mem_ctx, &r_u->sam, &r_u->uni_grp_name, num_entries, grp);
1116 init_samr_r_enum_dom_aliases(r_u, q_u->start_idx + num_entries, num_entries);
1118 DEBUG(5,("samr_enum_dom_aliases: %d\n", __LINE__));
1123 /*******************************************************************
1124 samr_reply_query_dispinfo
1125 ********************************************************************/
1126 NTSTATUS _samr_query_dispinfo(pipes_struct *p, SAMR_Q_QUERY_DISPINFO *q_u,
1127 SAMR_R_QUERY_DISPINFO *r_u)
1129 struct samr_info *info = NULL;
1130 uint32 struct_size=0x20; /* W2K always reply that, client doesn't care */
1132 uint32 max_entries=q_u->max_entries;
1133 uint32 enum_context=q_u->start_idx;
1134 uint32 max_size=q_u->max_size;
1136 SAM_DISPINFO_CTR *ctr;
1137 uint32 temp_size=0, total_data_size=0;
1139 uint32 num_account = 0;
1140 enum remote_arch_types ra_type = get_remote_arch();
1141 int max_sam_entries = (ra_type == RA_WIN95) ? MAX_SAM_ENTRIES_W95 : MAX_SAM_ENTRIES_W2K;
1144 DEBUG(5, ("samr_reply_query_dispinfo: %d\n", __LINE__));
1145 r_u->status = NT_STATUS_OK;
1147 /* find the policy handle. open a policy on it. */
1148 if (!find_policy_by_hnd(p, &q_u->domain_pol, (void **)&info))
1149 return NT_STATUS_INVALID_HANDLE;
1151 domain_sid = info->sid;
1154 * calculate how many entries we will return.
1156 * - the number of entries the client asked
1157 * - our limit on that
1158 * - the starting point (enumeration context)
1159 * - the buffer size the client will accept
1163 * We are a lot more like W2K. Instead of reading the SAM
1164 * each time to find the records we need to send back,
1165 * we read it once and link that copy to the sam handle.
1166 * For large user list (over the MAX_SAM_ENTRIES)
1167 * it's a definitive win.
1168 * second point to notice: between enumerations
1169 * our sam is now the same as it's a snapshoot.
1170 * third point: got rid of the static SAM_USER_21 struct
1171 * no more intermediate.
1172 * con: it uses much more memory, as a full copy is stored
1175 * If you want to change it, think twice and think
1176 * of the second point , that's really important.
1181 /* Get what we need from the password database */
1182 switch (q_u->switch_level) {
1184 /* When playing with usrmgr, this is necessary
1185 if you want immediate refresh after editing
1186 a user. I would like to do this after the
1187 setuserinfo2, but we do not have access to
1188 the domain handle in that call, only to the
1189 user handle. Where else does this hurt?
1193 /* We cannot do this here - it kills performace. JRA. */
1194 free_samr_users(info);
1199 /* Level 2 is for all machines, otherwise only 'normal' users */
1200 r_u->status=load_sampwd_entries(info, ACB_NORMAL, q_u->switch_level==2);
1202 if (!NT_STATUS_IS_OK(r_u->status)) {
1203 DEBUG(5, ("_samr_query_dispinfo: load_sampwd_entries failed\n"));
1206 num_account = info->disp_info.num_user_account;
1210 r_u->status = load_group_domain_entries(info, &info->sid);
1211 if (!NT_STATUS_IS_OK(r_u->status))
1213 num_account = info->disp_info.num_group_account;
1216 DEBUG(0,("_samr_query_dispinfo: Unknown info level (%u)\n", (unsigned int)q_u->switch_level ));
1217 return NT_STATUS_INVALID_INFO_CLASS;
1220 /* first limit the number of entries we will return */
1221 if(max_entries > max_sam_entries) {
1222 DEBUG(5, ("samr_reply_query_dispinfo: client requested %d entries, limiting to %d\n", max_entries, max_sam_entries));
1223 max_entries = max_sam_entries;
1226 if (enum_context > num_account) {
1227 DEBUG(5, ("samr_reply_query_dispinfo: enumeration handle over total entries\n"));
1228 return NT_STATUS_NO_MORE_ENTRIES;
1231 /* verify we won't overflow */
1232 if (max_entries > num_account-enum_context) {
1233 max_entries = num_account-enum_context;
1234 DEBUG(5, ("samr_reply_query_dispinfo: only %d entries to return\n", max_entries));
1237 /* calculate the size and limit on the number of entries we will return */
1238 temp_size=max_entries*struct_size;
1240 if (temp_size>max_size) {
1241 max_entries=MIN((max_size/struct_size),max_entries);;
1242 DEBUG(5, ("samr_reply_query_dispinfo: buffer size limits to only %d entries\n", max_entries));
1245 if (!(ctr = (SAM_DISPINFO_CTR *)talloc_zero(p->mem_ctx,sizeof(SAM_DISPINFO_CTR))))
1246 return NT_STATUS_NO_MEMORY;
1250 /* Now create reply structure */
1251 switch (q_u->switch_level) {
1254 if (!(ctr->sam.info1 = (SAM_DISPINFO_1 *)talloc_zero(p->mem_ctx,max_entries*sizeof(SAM_DISPINFO_1))))
1255 return NT_STATUS_NO_MEMORY;
1257 disp_ret = init_sam_dispinfo_1(p->mem_ctx, ctr->sam.info1, max_entries, enum_context,
1258 info->disp_info.disp_user_info, &domain_sid);
1259 if (!NT_STATUS_IS_OK(disp_ret))
1264 if (!(ctr->sam.info2 = (SAM_DISPINFO_2 *)talloc_zero(p->mem_ctx,max_entries*sizeof(SAM_DISPINFO_2))))
1265 return NT_STATUS_NO_MEMORY;
1267 disp_ret = init_sam_dispinfo_2(p->mem_ctx, ctr->sam.info2, max_entries, enum_context,
1268 info->disp_info.disp_user_info, &domain_sid);
1269 if (!NT_STATUS_IS_OK(disp_ret))
1274 if (!(ctr->sam.info3 = (SAM_DISPINFO_3 *)talloc_zero(p->mem_ctx,max_entries*sizeof(SAM_DISPINFO_3))))
1275 return NT_STATUS_NO_MEMORY;
1277 disp_ret = init_sam_dispinfo_3(p->mem_ctx, ctr->sam.info3, max_entries, enum_context, info->disp_info.disp_group_info);
1278 if (!NT_STATUS_IS_OK(disp_ret))
1283 if (!(ctr->sam.info4 = (SAM_DISPINFO_4 *)talloc_zero(p->mem_ctx,max_entries*sizeof(SAM_DISPINFO_4))))
1284 return NT_STATUS_NO_MEMORY;
1286 disp_ret = init_sam_dispinfo_4(p->mem_ctx, ctr->sam.info4, max_entries, enum_context, info->disp_info.disp_user_info);
1287 if (!NT_STATUS_IS_OK(disp_ret))
1292 if (!(ctr->sam.info5 = (SAM_DISPINFO_5 *)talloc_zero(p->mem_ctx,max_entries*sizeof(SAM_DISPINFO_5))))
1293 return NT_STATUS_NO_MEMORY;
1295 disp_ret = init_sam_dispinfo_5(p->mem_ctx, ctr->sam.info5, max_entries, enum_context, info->disp_info.disp_group_info);
1296 if (!NT_STATUS_IS_OK(disp_ret))
1301 ctr->sam.info = NULL;
1302 return NT_STATUS_INVALID_INFO_CLASS;
1305 /* calculate the total size */
1306 total_data_size=num_account*struct_size;
1308 if (enum_context+max_entries < num_account)
1309 r_u->status = STATUS_MORE_ENTRIES;
1311 DEBUG(5, ("_samr_query_dispinfo: %d\n", __LINE__));
1313 init_samr_r_query_dispinfo(r_u, max_entries, total_data_size, temp_size, q_u->switch_level, ctr, r_u->status);
1319 /*******************************************************************
1320 samr_reply_query_aliasinfo
1321 ********************************************************************/
1323 NTSTATUS _samr_query_aliasinfo(pipes_struct *p, SAMR_Q_QUERY_ALIASINFO *q_u, SAMR_R_QUERY_ALIASINFO *r_u)
1329 r_u->status = NT_STATUS_OK;
1331 DEBUG(5,("_samr_query_aliasinfo: %d\n", __LINE__));
1333 /* find the policy handle. open a policy on it. */
1334 if (!get_lsa_policy_samr_sid(p, &q_u->pol, &sid, &acc_granted))
1335 return NT_STATUS_INVALID_HANDLE;
1336 if (!NT_STATUS_IS_OK(r_u->status = access_check_samr_function(acc_granted, SA_RIGHT_ALIAS_LOOKUP_INFO, "_samr_query_aliasinfo"))) {
1340 if (!sid_check_is_in_our_domain(&sid) &&
1341 !sid_check_is_in_builtin(&sid))
1342 return NT_STATUS_OBJECT_TYPE_MISMATCH;
1344 if (!pdb_getgrsid(&map, sid, MAPPING_WITHOUT_PRIV))
1345 return NT_STATUS_NO_SUCH_ALIAS;
1347 switch (q_u->switch_level) {
1350 r_u->ctr.switch_value1 = 1;
1351 init_samr_alias_info1(&r_u->ctr.alias.info1, map.nt_name, 1, map.comment);
1355 r_u->ctr.switch_value1 = 3;
1356 init_samr_alias_info3(&r_u->ctr.alias.info3, map.comment);
1359 return NT_STATUS_INVALID_INFO_CLASS;
1362 DEBUG(5,("_samr_query_aliasinfo: %d\n", __LINE__));
1368 /*******************************************************************
1369 samr_reply_lookup_ids
1370 ********************************************************************/
1372 uint32 _samr_lookup_ids(pipes_struct *p, SAMR_Q_LOOKUP_IDS *q_u, SAMR_R_LOOKUP_IDS *r_u)
1374 uint32 rid[MAX_SAM_ENTRIES];
1375 int num_rids = q_u->num_sids1;
1377 r_u->status = NT_STATUS_OK;
1379 DEBUG(5,("_samr_lookup_ids: %d\n", __LINE__));
1381 if (num_rids > MAX_SAM_ENTRIES) {
1382 num_rids = MAX_SAM_ENTRIES;
1383 DEBUG(5,("_samr_lookup_ids: truncating entries to %d\n", num_rids));
1388 SMB_ASSERT_ARRAY(q_u->uni_user_name, num_rids);
1390 for (i = 0; i < num_rids && status == 0; i++)
1392 struct sam_passwd *sam_pass;
1396 fstrcpy(user_name, unistrn2(q_u->uni_user_name[i].buffer,
1397 q_u->uni_user_name[i].uni_str_len));
1399 /* find the user account */
1401 sam_pass = get_smb21pwd_entry(user_name, 0);
1404 if (sam_pass == NULL)
1406 status = 0xC0000000 | NT_STATUS_NO_SUCH_USER;
1411 rid[i] = sam_pass->user_rid;
1417 rid[0] = BUILTIN_ALIAS_RID_USERS;
1419 init_samr_r_lookup_ids(&r_u, num_rids, rid, NT_STATUS_OK);
1421 DEBUG(5,("_samr_lookup_ids: %d\n", __LINE__));
1427 /*******************************************************************
1429 ********************************************************************/
1431 NTSTATUS _samr_lookup_names(pipes_struct *p, SAMR_Q_LOOKUP_NAMES *q_u, SAMR_R_LOOKUP_NAMES *r_u)
1433 uint32 rid[MAX_SAM_ENTRIES];
1435 enum SID_NAME_USE type[MAX_SAM_ENTRIES];
1436 enum SID_NAME_USE local_type;
1438 int num_rids = q_u->num_names2;
1443 r_u->status = NT_STATUS_OK;
1445 DEBUG(5,("_samr_lookup_names: %d\n", __LINE__));
1450 if (!get_lsa_policy_samr_sid(p, &q_u->pol, &pol_sid, &acc_granted)) {
1451 init_samr_r_lookup_names(p->mem_ctx, r_u, 0, NULL, NULL, NT_STATUS_OBJECT_TYPE_MISMATCH);
1455 if (!NT_STATUS_IS_OK(r_u->status = access_check_samr_function(acc_granted, 0, "_samr_lookup_names"))) { /* Don't know the acc_bits yet */
1459 if (num_rids > MAX_SAM_ENTRIES) {
1460 num_rids = MAX_SAM_ENTRIES;
1461 DEBUG(5,("_samr_lookup_names: truncating entries to %d\n", num_rids));
1464 DEBUG(5,("_samr_lookup_names: looking name on SID %s\n", sid_to_string(sid_str, &pol_sid)));
1466 become_root(); /* local_lookup_name can require root privs */
1468 for (i = 0; i < num_rids; i++) {
1472 r_u->status = NT_STATUS_NONE_MAPPED;
1474 rid [i] = 0xffffffff;
1475 type[i] = SID_NAME_UNKNOWN;
1477 rpcstr_pull(name, q_u->uni_name[i].buffer, sizeof(name), q_u->uni_name[i].uni_str_len*2, 0);
1480 * we are only looking for a name
1481 * the SID we get back can be outside
1482 * the scope of the pol_sid
1484 * in clear: it prevents to reply to domain\group: yes
1485 * when only builtin\group exists.
1487 * a cleaner code is to add the sid of the domain we're looking in
1488 * to the local_lookup_name function.
1490 if(local_lookup_name(name, &sid, &local_type)) {
1491 sid_split_rid(&sid, &local_rid);
1493 if (sid_equal(&sid, &pol_sid)) {
1496 r_u->status = NT_STATUS_OK;
1503 init_samr_r_lookup_names(p->mem_ctx, r_u, num_rids, rid, (uint32 *)type, r_u->status);
1505 DEBUG(5,("_samr_lookup_names: %d\n", __LINE__));
1510 /*******************************************************************
1511 _samr_chgpasswd_user
1512 ********************************************************************/
1514 NTSTATUS _samr_chgpasswd_user(pipes_struct *p, SAMR_Q_CHGPASSWD_USER *q_u, SAMR_R_CHGPASSWD_USER *r_u)
1519 DEBUG(5,("_samr_chgpasswd_user: %d\n", __LINE__));
1521 r_u->status = NT_STATUS_OK;
1523 rpcstr_pull(user_name, q_u->uni_user_name.buffer, sizeof(user_name), q_u->uni_user_name.uni_str_len*2, 0);
1524 rpcstr_pull(wks, q_u->uni_dest_host.buffer, sizeof(wks), q_u->uni_dest_host.uni_str_len*2,0);
1526 DEBUG(5,("samr_chgpasswd_user: user: %s wks: %s\n", user_name, wks));
1529 * Pass the user through the NT -> unix user mapping
1533 (void)map_username(user_name);
1536 * UNIX username case mangling not required, pass_oem_change
1537 * is case insensitive.
1540 r_u->status = pass_oem_change(user_name, q_u->lm_newpass.pass, q_u->lm_oldhash.hash,
1541 q_u->nt_newpass.pass, q_u->nt_oldhash.hash);
1543 init_samr_r_chgpasswd_user(r_u, r_u->status);
1545 DEBUG(5,("_samr_chgpasswd_user: %d\n", __LINE__));
1550 /*******************************************************************
1551 makes a SAMR_R_LOOKUP_RIDS structure.
1552 ********************************************************************/
1554 static BOOL make_samr_lookup_rids(TALLOC_CTX *ctx, uint32 num_names, fstring names[],
1555 UNIHDR **pp_hdr_name, UNISTR2 **pp_uni_name)
1558 UNIHDR *hdr_name=NULL;
1559 UNISTR2 *uni_name=NULL;
1561 *pp_uni_name = NULL;
1562 *pp_hdr_name = NULL;
1564 if (num_names != 0) {
1565 hdr_name = (UNIHDR *)talloc_zero(ctx, sizeof(UNIHDR)*num_names);
1566 if (hdr_name == NULL)
1569 uni_name = (UNISTR2 *)talloc_zero(ctx,sizeof(UNISTR2)*num_names);
1570 if (uni_name == NULL)
1574 for (i = 0; i < num_names; i++) {
1575 int len = names[i] != NULL ? strlen(names[i]) : 0;
1576 DEBUG(10, ("names[%d]:%s\n", i, names[i]));
1577 init_uni_hdr(&hdr_name[i], len);
1578 init_unistr2(&uni_name[i], names[i], len);
1581 *pp_uni_name = uni_name;
1582 *pp_hdr_name = hdr_name;
1587 /*******************************************************************
1589 ********************************************************************/
1591 NTSTATUS _samr_lookup_rids(pipes_struct *p, SAMR_Q_LOOKUP_RIDS *q_u, SAMR_R_LOOKUP_RIDS *r_u)
1593 fstring group_names[MAX_SAM_ENTRIES];
1594 uint32 *group_attrs = NULL;
1595 UNIHDR *hdr_name = NULL;
1596 UNISTR2 *uni_name = NULL;
1598 int num_rids = q_u->num_rids1;
1602 r_u->status = NT_STATUS_OK;
1604 DEBUG(5,("_samr_lookup_rids: %d\n", __LINE__));
1606 /* find the policy handle. open a policy on it. */
1607 if (!get_lsa_policy_samr_sid(p, &q_u->pol, &pol_sid, &acc_granted))
1608 return NT_STATUS_INVALID_HANDLE;
1610 if (num_rids > MAX_SAM_ENTRIES) {
1611 num_rids = MAX_SAM_ENTRIES;
1612 DEBUG(5,("_samr_lookup_rids: truncating entries to %d\n", num_rids));
1616 if ((group_attrs = (uint32 *)talloc_zero(p->mem_ctx, num_rids * sizeof(uint32))) == NULL)
1617 return NT_STATUS_NO_MEMORY;
1620 r_u->status = NT_STATUS_NONE_MAPPED;
1622 become_root(); /* lookup_sid can require root privs */
1624 for (i = 0; i < num_rids; i++) {
1628 enum SID_NAME_USE type;
1630 group_attrs[i] = SID_NAME_UNKNOWN;
1631 *group_names[i] = '\0';
1633 if (sid_equal(&pol_sid, get_global_sam_sid())) {
1634 sid_copy(&sid, &pol_sid);
1635 sid_append_rid(&sid, q_u->rid[i]);
1637 if (lookup_sid(&sid, domname, tmpname, &type)) {
1638 r_u->status = NT_STATUS_OK;
1639 group_attrs[i] = (uint32)type;
1640 fstrcpy(group_names[i],tmpname);
1641 DEBUG(5,("_samr_lookup_rids: %s:%d\n", group_names[i], group_attrs[i]));
1648 if(!make_samr_lookup_rids(p->mem_ctx, num_rids, group_names, &hdr_name, &uni_name))
1649 return NT_STATUS_NO_MEMORY;
1651 init_samr_r_lookup_rids(r_u, num_rids, hdr_name, uni_name, group_attrs);
1653 DEBUG(5,("_samr_lookup_rids: %d\n", __LINE__));
1658 /*******************************************************************
1659 _api_samr_open_user. Safe - gives out no passwd info.
1660 ********************************************************************/
1662 NTSTATUS _api_samr_open_user(pipes_struct *p, SAMR_Q_OPEN_USER *q_u, SAMR_R_OPEN_USER *r_u)
1664 SAM_ACCOUNT *sampass=NULL;
1666 POLICY_HND domain_pol = q_u->domain_pol;
1667 POLICY_HND *user_pol = &r_u->user_pol;
1668 struct samr_info *info = NULL;
1669 SEC_DESC *psd = NULL;
1671 uint32 des_access = q_u->access_mask;
1676 r_u->status = NT_STATUS_OK;
1678 /* find the domain policy handle and get domain SID / access bits in the domain policy. */
1679 if (!get_lsa_policy_samr_sid(p, &domain_pol, &sid, &acc_granted))
1680 return NT_STATUS_INVALID_HANDLE;
1682 if (!NT_STATUS_IS_OK(nt_status = access_check_samr_function(acc_granted, SA_RIGHT_DOMAIN_OPEN_ACCOUNT, "_samr_open_user"))) {
1686 nt_status = pdb_init_sam_talloc(p->mem_ctx, &sampass);
1687 if (!NT_STATUS_IS_OK(nt_status)) {
1691 /* append the user's RID to it */
1692 if (!sid_append_rid(&sid, q_u->user_rid))
1693 return NT_STATUS_NO_SUCH_USER;
1695 /* check if access can be granted as requested by client. */
1696 samr_make_usr_obj_sd(p->mem_ctx, &psd, &sd_size, &sid);
1697 se_map_generic(&des_access, &usr_generic_mapping);
1698 if (!NT_STATUS_IS_OK(nt_status =
1699 access_check_samr_object(psd, p->pipe_user.nt_user_token,
1700 des_access, &acc_granted, "_samr_open_user"))) {
1705 ret=pdb_getsampwsid(sampass, &sid);
1708 /* check that the SID exists in our domain. */
1710 return NT_STATUS_NO_SUCH_USER;
1713 pdb_free_sam(&sampass);
1715 /* associate the user's SID and access bits with the new handle. */
1716 if ((info = get_samr_info_by_sid(&sid)) == NULL)
1717 return NT_STATUS_NO_MEMORY;
1718 info->acc_granted = acc_granted;
1720 /* get a (unique) handle. open a policy on it. */
1721 if (!create_policy_hnd(p, user_pol, free_samr_info, (void *)info))
1722 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
1727 /*************************************************************************
1728 get_user_info_10. Safe. Only gives out acb bits.
1729 *************************************************************************/
1731 static NTSTATUS get_user_info_10(TALLOC_CTX *mem_ctx, SAM_USER_INFO_10 *id10, DOM_SID *user_sid)
1733 SAM_ACCOUNT *smbpass=NULL;
1737 nt_status = pdb_init_sam_talloc(mem_ctx, &smbpass);
1739 if (!NT_STATUS_IS_OK(nt_status)) {
1744 ret = pdb_getsampwsid(smbpass, user_sid);
1748 DEBUG(4,("User %s not found\n", sid_string_static(user_sid)));
1749 return NT_STATUS_NO_SUCH_USER;
1752 DEBUG(3,("User:[%s]\n", pdb_get_username(smbpass) ));
1755 init_sam_user_info10(id10, pdb_get_acct_ctrl(smbpass) );
1757 pdb_free_sam(&smbpass);
1759 return NT_STATUS_OK;
1762 /*************************************************************************
1763 get_user_info_12. OK - this is the killer as it gives out password info.
1764 Ensure that this is only allowed on an encrypted connection with a root
1766 *************************************************************************/
1768 static NTSTATUS get_user_info_12(pipes_struct *p, TALLOC_CTX *mem_ctx, SAM_USER_INFO_12 * id12, DOM_SID *user_sid)
1770 SAM_ACCOUNT *smbpass=NULL;
1774 if (!p->ntlmssp_auth_validated)
1775 return NT_STATUS_ACCESS_DENIED;
1777 if (!(p->ntlmssp_chal_flags & NTLMSSP_NEGOTIATE_SIGN) || !(p->ntlmssp_chal_flags & NTLMSSP_NEGOTIATE_SEAL))
1778 return NT_STATUS_ACCESS_DENIED;
1781 * Do *NOT* do become_root()/unbecome_root() here ! JRA.
1784 nt_status = pdb_init_sam_talloc(mem_ctx, &smbpass);
1786 if (!NT_STATUS_IS_OK(nt_status)) {
1790 ret = pdb_getsampwsid(smbpass, user_sid);
1793 DEBUG(4, ("User %s not found\n", sid_string_static(user_sid)));
1794 pdb_free_sam(&smbpass);
1795 return (geteuid() == (uid_t)0) ? NT_STATUS_NO_SUCH_USER : NT_STATUS_ACCESS_DENIED;
1798 DEBUG(3,("User:[%s] 0x%x\n", pdb_get_username(smbpass), pdb_get_acct_ctrl(smbpass) ));
1800 if ( pdb_get_acct_ctrl(smbpass) & ACB_DISABLED) {
1801 pdb_free_sam(&smbpass);
1802 return NT_STATUS_ACCOUNT_DISABLED;
1806 init_sam_user_info12(id12, pdb_get_lanman_passwd(smbpass), pdb_get_nt_passwd(smbpass));
1808 pdb_free_sam(&smbpass);
1810 return NT_STATUS_OK;
1813 /*************************************************************************
1815 *************************************************************************/
1817 static NTSTATUS get_user_info_20(TALLOC_CTX *mem_ctx, SAM_USER_INFO_20 *id20, DOM_SID *user_sid)
1819 SAM_ACCOUNT *sampass=NULL;
1822 pdb_init_sam_talloc(mem_ctx, &sampass);
1825 ret = pdb_getsampwsid(sampass, user_sid);
1829 DEBUG(4,("User %s not found\n", sid_string_static(user_sid)));
1830 return NT_STATUS_NO_SUCH_USER;
1833 samr_clear_sam_passwd(sampass);
1835 DEBUG(3,("User:[%s]\n", pdb_get_username(sampass) ));
1838 init_sam_user_info20A(id20, sampass);
1840 pdb_free_sam(&sampass);
1842 return NT_STATUS_OK;
1845 /*************************************************************************
1847 *************************************************************************/
1849 static NTSTATUS get_user_info_21(TALLOC_CTX *mem_ctx, SAM_USER_INFO_21 *id21,
1850 DOM_SID *user_sid, DOM_SID *domain_sid)
1852 SAM_ACCOUNT *sampass=NULL;
1856 nt_status = pdb_init_sam_talloc(mem_ctx, &sampass);
1857 if (!NT_STATUS_IS_OK(nt_status)) {
1862 ret = pdb_getsampwsid(sampass, user_sid);
1866 DEBUG(4,("User %s not found\n", sid_string_static(user_sid)));
1867 return NT_STATUS_NO_SUCH_USER;
1870 samr_clear_sam_passwd(sampass);
1872 DEBUG(3,("User:[%s]\n", pdb_get_username(sampass) ));
1875 nt_status = init_sam_user_info21A(id21, sampass, domain_sid);
1877 pdb_free_sam(&sampass);
1879 return NT_STATUS_OK;
1882 /*******************************************************************
1883 _samr_query_userinfo
1884 ********************************************************************/
1886 NTSTATUS _samr_query_userinfo(pipes_struct *p, SAMR_Q_QUERY_USERINFO *q_u, SAMR_R_QUERY_USERINFO *r_u)
1888 SAM_USERINFO_CTR *ctr;
1889 struct samr_info *info = NULL;
1893 r_u->status=NT_STATUS_OK;
1895 /* search for the handle */
1896 if (!find_policy_by_hnd(p, &q_u->pol, (void **)&info))
1897 return NT_STATUS_INVALID_HANDLE;
1899 domain_sid = info->sid;
1901 sid_split_rid(&domain_sid, &rid);
1903 if (!sid_check_is_in_our_domain(&info->sid))
1904 return NT_STATUS_OBJECT_TYPE_MISMATCH;
1906 DEBUG(5,("_samr_query_userinfo: sid:%s\n", sid_string_static(&info->sid)));
1908 ctr = (SAM_USERINFO_CTR *)talloc_zero(p->mem_ctx, sizeof(SAM_USERINFO_CTR));
1910 return NT_STATUS_NO_MEMORY;
1914 /* ok! user info levels (lots: see MSDEV help), off we go... */
1915 ctr->switch_value = q_u->switch_value;
1917 switch (q_u->switch_value) {
1919 ctr->info.id10 = (SAM_USER_INFO_10 *)talloc_zero(p->mem_ctx, sizeof(SAM_USER_INFO_10));
1920 if (ctr->info.id10 == NULL)
1921 return NT_STATUS_NO_MEMORY;
1923 if (!NT_STATUS_IS_OK(r_u->status = get_user_info_10(p->mem_ctx, ctr->info.id10, &info->sid)))
1928 /* whoops - got this wrong. i think. or don't understand what's happening. */
1932 info = (void *)&id11;
1934 expire.low = 0xffffffff;
1935 expire.high = 0x7fffffff;
1937 ctr->info.id = (SAM_USER_INFO_11 *)talloc_zero(p->mem_ctx,
1942 ZERO_STRUCTP(ctr->info.id11);
1943 init_sam_user_info11(ctr->info.id11, &expire,
1944 "BROOKFIELDS$", /* name */
1945 0x03ef, /* user rid */
1946 0x201, /* group rid */
1947 0x0080); /* acb info */
1954 ctr->info.id12 = (SAM_USER_INFO_12 *)talloc_zero(p->mem_ctx, sizeof(SAM_USER_INFO_12));
1955 if (ctr->info.id12 == NULL)
1956 return NT_STATUS_NO_MEMORY;
1958 if (!NT_STATUS_IS_OK(r_u->status = get_user_info_12(p, p->mem_ctx, ctr->info.id12, &info->sid)))
1963 ctr->info.id20 = (SAM_USER_INFO_20 *)talloc_zero(p->mem_ctx,sizeof(SAM_USER_INFO_20));
1964 if (ctr->info.id20 == NULL)
1965 return NT_STATUS_NO_MEMORY;
1966 if (!NT_STATUS_IS_OK(r_u->status = get_user_info_20(p->mem_ctx, ctr->info.id20, &info->sid)))
1971 ctr->info.id21 = (SAM_USER_INFO_21 *)talloc_zero(p->mem_ctx,sizeof(SAM_USER_INFO_21));
1972 if (ctr->info.id21 == NULL)
1973 return NT_STATUS_NO_MEMORY;
1974 if (!NT_STATUS_IS_OK(r_u->status = get_user_info_21(p->mem_ctx, ctr->info.id21,
1975 &info->sid, &domain_sid)))
1980 return NT_STATUS_INVALID_INFO_CLASS;
1983 init_samr_r_query_userinfo(r_u, ctr, r_u->status);
1985 DEBUG(5,("_samr_query_userinfo: %d\n", __LINE__));
1990 /*******************************************************************
1991 samr_reply_query_usergroups
1992 ********************************************************************/
1994 NTSTATUS _samr_query_usergroups(pipes_struct *p, SAMR_Q_QUERY_USERGROUPS *q_u, SAMR_R_QUERY_USERGROUPS *r_u)
1996 SAM_ACCOUNT *sam_pass=NULL;
1998 DOM_GID *gids = NULL;
2004 * from the SID in the request:
2005 * we should send back the list of DOMAIN GROUPS
2006 * the user is a member of
2008 * and only the DOMAIN GROUPS
2009 * no ALIASES !!! neither aliases of the domain
2010 * nor aliases of the builtin SID
2015 r_u->status = NT_STATUS_OK;
2017 DEBUG(5,("_samr_query_usergroups: %d\n", __LINE__));
2019 /* find the policy handle. open a policy on it. */
2020 if (!get_lsa_policy_samr_sid(p, &q_u->pol, &sid, &acc_granted))
2021 return NT_STATUS_INVALID_HANDLE;
2023 if (!NT_STATUS_IS_OK(r_u->status = access_check_samr_function(acc_granted, SA_RIGHT_USER_GET_GROUPS, "_samr_query_usergroups"))) {
2027 if (!sid_check_is_in_our_domain(&sid))
2028 return NT_STATUS_OBJECT_TYPE_MISMATCH;
2030 pdb_init_sam(&sam_pass);
2033 ret = pdb_getsampwsid(sam_pass, &sid);
2037 pdb_free_sam(&sam_pass);
2038 return NT_STATUS_NO_SUCH_USER;
2041 if(!get_domain_user_groups(p->mem_ctx, &num_groups, &gids, sam_pass)) {
2042 pdb_free_sam(&sam_pass);
2043 return NT_STATUS_NO_SUCH_GROUP;
2046 /* construct the response. lkclXXXX: gids are not copied! */
2047 init_samr_r_query_usergroups(r_u, num_groups, gids, r_u->status);
2049 DEBUG(5,("_samr_query_usergroups: %d\n", __LINE__));
2051 pdb_free_sam(&sam_pass);
2056 /*******************************************************************
2057 _samr_query_dom_info
2058 ********************************************************************/
2060 NTSTATUS _samr_query_dom_info(pipes_struct *p, SAMR_Q_QUERY_DOMAIN_INFO *q_u, SAMR_R_QUERY_DOMAIN_INFO *r_u)
2062 struct samr_info *info = NULL;
2064 uint32 min_pass_len,pass_hist,flag;
2065 time_t u_expire, u_min_age;
2066 NTTIME nt_expire, nt_min_age;
2068 time_t u_lock_duration, u_reset_time;
2069 NTTIME nt_lock_duration, nt_reset_time;
2075 uint32 account_policy_temp;
2077 uint32 num_users=0, num_groups=0, num_aliases=0;
2079 if ((ctr = (SAM_UNK_CTR *)talloc_zero(p->mem_ctx, sizeof(SAM_UNK_CTR))) == NULL)
2080 return NT_STATUS_NO_MEMORY;
2084 r_u->status = NT_STATUS_OK;
2086 DEBUG(5,("_samr_query_dom_info: %d\n", __LINE__));
2088 /* find the policy handle. open a policy on it. */
2089 if (!find_policy_by_hnd(p, &q_u->domain_pol, (void **)&info))
2090 return NT_STATUS_INVALID_HANDLE;
2092 switch (q_u->switch_value) {
2095 account_policy_get(AP_MIN_PASSWORD_LEN, &account_policy_temp);
2096 min_pass_len = account_policy_temp;
2098 account_policy_get(AP_PASSWORD_HISTORY, &account_policy_temp);
2099 pass_hist = account_policy_temp;
2101 account_policy_get(AP_USER_MUST_LOGON_TO_CHG_PASS, &account_policy_temp);
2102 flag = account_policy_temp;
2104 account_policy_get(AP_MAX_PASSWORD_AGE, &account_policy_temp);
2105 u_expire = account_policy_temp;
2107 account_policy_get(AP_MIN_PASSWORD_AGE, &account_policy_temp);
2108 u_min_age = account_policy_temp;
2110 unix_to_nt_time_abs(&nt_expire, u_expire);
2111 unix_to_nt_time_abs(&nt_min_age, u_min_age);
2113 init_unk_info1(&ctr->info.inf1, (uint16)min_pass_len, (uint16)pass_hist,
2114 flag, nt_expire, nt_min_age);
2118 r_u->status=load_sampwd_entries(info, ACB_NORMAL, False);
2120 if (!NT_STATUS_IS_OK(r_u->status)) {
2121 DEBUG(5, ("_samr_query_dispinfo: load_sampwd_entries failed\n"));
2124 num_users=info->disp_info.num_user_account;
2127 r_u->status=load_group_domain_entries(info, get_global_sam_sid());
2128 if (!NT_STATUS_IS_OK(r_u->status)) {
2129 DEBUG(5, ("_samr_query_dispinfo: load_group_domain_entries failed\n"));
2132 num_groups=info->disp_info.num_group_account;
2135 /* The time call below is to get a sequence number for the sam. FIXME !!! JRA. */
2136 init_unk_info2(&ctr->info.inf2, lp_workgroup(), global_myname(), (uint32) time(NULL),
2137 num_users, num_groups, num_aliases);
2140 account_policy_get(AP_TIME_TO_LOGOUT, (int *)&u_logout);
2141 unix_to_nt_time_abs(&nt_logout, u_logout);
2143 init_unk_info3(&ctr->info.inf3, nt_logout);
2146 init_unk_info5(&ctr->info.inf5, global_myname());
2149 init_unk_info6(&ctr->info.inf6);
2152 init_unk_info7(&ctr->info.inf7);
2155 account_policy_get(AP_LOCK_ACCOUNT_DURATION, &account_policy_temp);
2156 u_lock_duration = account_policy_temp;
2158 account_policy_get(AP_RESET_COUNT_TIME, &account_policy_temp);
2159 u_reset_time = account_policy_temp;
2161 account_policy_get(AP_BAD_ATTEMPT_LOCKOUT, &account_policy_temp);
2162 lockout = account_policy_temp;
2164 unix_to_nt_time_abs(&nt_lock_duration, u_lock_duration);
2165 unix_to_nt_time_abs(&nt_reset_time, u_reset_time);
2167 init_unk_info12(&ctr->info.inf12, nt_lock_duration, nt_reset_time, (uint16)lockout);
2170 return NT_STATUS_INVALID_INFO_CLASS;
2173 init_samr_r_query_dom_info(r_u, q_u->switch_value, ctr, NT_STATUS_OK);
2175 DEBUG(5,("_samr_query_dom_info: %d\n", __LINE__));
2180 /*******************************************************************
2181 _api_samr_create_user
2182 Create an account, can be either a normal user or a machine.
2183 This funcion will need to be updated for bdc/domain trusts.
2184 ********************************************************************/
2186 NTSTATUS _api_samr_create_user(pipes_struct *p, SAMR_Q_CREATE_USER *q_u, SAMR_R_CREATE_USER *r_u)
2188 SAM_ACCOUNT *sam_pass=NULL;
2192 POLICY_HND dom_pol = q_u->domain_pol;
2193 UNISTR2 user_account = q_u->uni_name;
2194 uint16 acb_info = q_u->acb_info;
2195 POLICY_HND *user_pol = &r_u->user_pol;
2196 struct samr_info *info = NULL;
2203 uint32 des_access = GENERIC_RIGHTS_USER_ALL_ACCESS;
2205 /* Get the domain SID stored in the domain policy */
2206 if (!get_lsa_policy_samr_sid(p, &dom_pol, &sid, &acc_granted))
2207 return NT_STATUS_INVALID_HANDLE;
2209 if (!NT_STATUS_IS_OK(nt_status = access_check_samr_function(acc_granted, SA_RIGHT_DOMAIN_CREATE_USER, "_samr_create_user"))) {
2213 /* find the account: tell the caller if it exists.
2214 lkclXXXX i have *no* idea if this is a problem or not
2215 or even if you are supposed to construct a different
2216 reply if the account already exists...
2219 rpcstr_pull(account, user_account.buffer, sizeof(account), user_account.uni_str_len*2, 0);
2222 pdb_init_sam(&sam_pass);
2225 ret = pdb_getsampwnam(sam_pass, account);
2228 /* this account exists: say so */
2229 pdb_free_sam(&sam_pass);
2230 return NT_STATUS_USER_EXISTS;
2233 pdb_free_sam(&sam_pass);
2236 * NB. VERY IMPORTANT ! This call must be done as the current pipe user,
2237 * *NOT* surrounded by a become_root()/unbecome_root() call. This ensures
2238 * that only people with write access to the smbpasswd file will be able
2239 * to create a user. JRA.
2243 * add the user in the /etc/passwd file or the unix authority system.
2244 * We don't check if the smb_create_user() function succed or not for 2 reasons:
2245 * a) local_password_change() checks for us if the /etc/passwd account really exists
2246 * b) smb_create_user() would return an error if the account already exists
2247 * and as it could return an error also if it can't create the account, it would be tricky.
2249 * So we go the easy way, only check after if the account exists.
2250 * JFM (2/3/2001), to clear any possible bad understanding (-:
2252 * We now have seperate script paramaters for adding users/machines so we
2253 * now have some sainity-checking to match.
2256 DEBUG(10,("checking account %s at pos %d for $ termination\n",account, strlen(account)-1));
2258 if ((acb_info & ACB_WSTRUST) && (account[strlen(account)-1] == '$')) {
2259 pstrcpy(add_script, lp_addmachine_script());
2260 } else if ((!(acb_info & ACB_WSTRUST)) && (account[strlen(account)-1] != '$')) {
2261 pstrcpy(add_script, lp_adduser_script());
2263 DEBUG(0, ("_api_samr_create_user: mismatch between trust flags and $ termination\n"));
2264 pdb_free_sam(&sam_pass);
2265 return NT_STATUS_UNSUCCESSFUL;
2270 * we can't check both the ending $ and the acb_info.
2272 * UserManager creates trust accounts (ending in $,
2273 * normal that hidden accounts) with the acb_info equals to ACB_NORMAL.
2276 if (account[strlen(account)-1] == '$')
2277 pstrcpy(add_script, lp_addmachine_script());
2279 pstrcpy(add_script, lp_adduser_script());
2283 all_string_sub(add_script, "%u", account, sizeof(account));
2284 add_ret = smbrun(add_script,NULL);
2285 DEBUG(3,("_api_samr_create_user: Running the command `%s' gave %d\n", add_script, add_ret));
2288 if (!NT_STATUS_IS_OK(nt_status = pdb_init_sam(&sam_pass))) {
2292 pw = getpwnam_alloc(account);
2297 if (!uid_to_sid(&user_sid, pw->pw_uid)) {
2298 passwd_free(&pw); /* done with this now */
2299 pdb_free_sam(&sam_pass);
2300 DEBUG(1, ("_api_samr_create_user: uid_to_sid failed, cannot add user.\n"));
2301 return NT_STATUS_ACCESS_DENIED;
2304 if (!pdb_set_user_sid(sam_pass, &user_sid, PDB_CHANGED)) {
2305 passwd_free(&pw); /* done with this now */
2306 pdb_free_sam(&sam_pass);
2307 return NT_STATUS_NO_MEMORY;
2310 if (!gid_to_sid(&group_sid, pw->pw_gid)) {
2311 passwd_free(&pw); /* done with this now */
2312 pdb_free_sam(&sam_pass);
2313 DEBUG(1, ("_api_samr_create_user: gid_to_sid failed, cannot add user.\n"));
2314 return NT_STATUS_ACCESS_DENIED;
2317 if (!pdb_set_group_sid(sam_pass, &group_sid, PDB_CHANGED)) {
2318 passwd_free(&pw); /* done with this now */
2319 pdb_free_sam(&sam_pass);
2320 return NT_STATUS_NO_MEMORY;
2323 passwd_free(&pw); /* done with this now */
2325 DEBUG(3,("attempting to create non-unix account %s\n", account));
2329 if (!pdb_set_username(sam_pass, account, PDB_CHANGED)) {
2330 pdb_free_sam(&sam_pass);
2331 return NT_STATUS_NO_MEMORY;
2334 pdb_set_acct_ctrl(sam_pass, acb_info, PDB_CHANGED);
2336 if (!pdb_add_sam_account(sam_pass)) {
2337 pdb_free_sam(&sam_pass);
2338 DEBUG(0, ("could not add user/computer %s to passdb. Check permissions?\n",
2340 return NT_STATUS_ACCESS_DENIED;
2343 pdb_reset_sam(sam_pass);
2345 if (!pdb_getsampwnam(sam_pass, account)) {
2346 pdb_free_sam(&sam_pass);
2347 DEBUG(0, ("could not find user/computer %s just added to passdb?!?\n",
2349 return NT_STATUS_ACCESS_DENIED;
2352 /* Get the user's SID */
2353 sid_copy(&sid, pdb_get_user_sid(sam_pass));
2355 samr_make_usr_obj_sd(p->mem_ctx, &psd, &sd_size, &sid);
2356 se_map_generic(&des_access, &usr_generic_mapping);
2357 if (!NT_STATUS_IS_OK(nt_status =
2358 access_check_samr_object(psd, p->pipe_user.nt_user_token,
2359 des_access, &acc_granted, "_samr_create_user"))) {
2363 /* associate the user's SID with the new handle. */
2364 if ((info = get_samr_info_by_sid(&sid)) == NULL) {
2365 pdb_free_sam(&sam_pass);
2366 return NT_STATUS_NO_MEMORY;
2371 info->acc_granted = acc_granted;
2373 /* get a (unique) handle. open a policy on it. */
2374 if (!create_policy_hnd(p, user_pol, free_samr_info, (void *)info)) {
2375 pdb_free_sam(&sam_pass);
2376 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
2379 r_u->user_rid=pdb_get_user_rid(sam_pass);
2381 r_u->access_granted = acc_granted;
2383 pdb_free_sam(&sam_pass);
2385 return NT_STATUS_OK;
2388 /*******************************************************************
2389 samr_reply_connect_anon
2390 ********************************************************************/
2392 NTSTATUS _samr_connect_anon(pipes_struct *p, SAMR_Q_CONNECT_ANON *q_u, SAMR_R_CONNECT_ANON *r_u)
2394 struct samr_info *info = NULL;
2398 if (!pipe_access_check(p)) {
2399 DEBUG(3, ("access denied to samr_connect_anon\n"));
2400 r_u->status = NT_STATUS_ACCESS_DENIED;
2404 /* set up the SAMR connect_anon response */
2406 r_u->status = NT_STATUS_OK;
2408 /* associate the user's SID with the new handle. */
2409 if ((info = get_samr_info_by_sid(NULL)) == NULL)
2410 return NT_STATUS_NO_MEMORY;
2412 info->status = q_u->unknown_0;
2414 /* get a (unique) handle. open a policy on it. */
2415 if (!create_policy_hnd(p, &r_u->connect_pol, free_samr_info, (void *)info))
2416 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
2421 /*******************************************************************
2423 ********************************************************************/
2425 NTSTATUS _samr_connect(pipes_struct *p, SAMR_Q_CONNECT *q_u, SAMR_R_CONNECT *r_u)
2427 struct samr_info *info = NULL;
2428 SEC_DESC *psd = NULL;
2430 uint32 des_access = q_u->access_mask;
2435 DEBUG(5,("_samr_connect: %d\n", __LINE__));
2439 if (!pipe_access_check(p)) {
2440 DEBUG(3, ("access denied to samr_connect\n"));
2441 r_u->status = NT_STATUS_ACCESS_DENIED;
2445 samr_make_sam_obj_sd(p->mem_ctx, &psd, &sd_size);
2446 se_map_generic(&des_access, &sam_generic_mapping);
2447 if (!NT_STATUS_IS_OK(nt_status =
2448 access_check_samr_object(psd, p->pipe_user.nt_user_token,
2449 des_access, &acc_granted, "_samr_connect"))) {
2453 r_u->status = NT_STATUS_OK;
2455 /* associate the user's SID and access granted with the new handle. */
2456 if ((info = get_samr_info_by_sid(NULL)) == NULL)
2457 return NT_STATUS_NO_MEMORY;
2459 info->acc_granted = acc_granted;
2460 info->status = q_u->access_mask;
2462 /* get a (unique) handle. open a policy on it. */
2463 if (!create_policy_hnd(p, &r_u->connect_pol, free_samr_info, (void *)info))
2464 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
2466 DEBUG(5,("_samr_connect: %d\n", __LINE__));
2471 /*******************************************************************
2473 ********************************************************************/
2475 NTSTATUS _samr_connect4(pipes_struct *p, SAMR_Q_CONNECT4 *q_u, SAMR_R_CONNECT4 *r_u)
2477 struct samr_info *info = NULL;
2478 SEC_DESC *psd = NULL;
2480 uint32 des_access = q_u->access_mask;
2485 DEBUG(5,("_samr_connect4: %d\n", __LINE__));
2489 if (!pipe_access_check(p)) {
2490 DEBUG(3, ("access denied to samr_connect4\n"));
2491 r_u->status = NT_STATUS_ACCESS_DENIED;
2495 samr_make_sam_obj_sd(p->mem_ctx, &psd, &sd_size);
2496 se_map_generic(&des_access, &sam_generic_mapping);
2497 if (!NT_STATUS_IS_OK(nt_status =
2498 access_check_samr_object(psd, p->pipe_user.nt_user_token,
2499 des_access, &acc_granted, "_samr_connect"))) {
2503 r_u->status = NT_STATUS_OK;
2505 /* associate the user's SID and access granted with the new handle. */
2506 if ((info = get_samr_info_by_sid(NULL)) == NULL)
2507 return NT_STATUS_NO_MEMORY;
2509 info->acc_granted = acc_granted;
2510 info->status = q_u->access_mask;
2512 /* get a (unique) handle. open a policy on it. */
2513 if (!create_policy_hnd(p, &r_u->connect_pol, free_samr_info, (void *)info))
2514 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
2516 DEBUG(5,("_samr_connect: %d\n", __LINE__));
2521 /**********************************************************************
2522 api_samr_lookup_domain
2523 **********************************************************************/
2525 NTSTATUS _samr_lookup_domain(pipes_struct *p, SAMR_Q_LOOKUP_DOMAIN *q_u, SAMR_R_LOOKUP_DOMAIN *r_u)
2527 struct samr_info *info;
2528 fstring domain_name;
2531 r_u->status = NT_STATUS_OK;
2533 if (!find_policy_by_hnd(p, &q_u->connect_pol, (void**)&info))
2534 return NT_STATUS_INVALID_HANDLE;
2536 if (!NT_STATUS_IS_OK(r_u->status = access_check_samr_function(info->acc_granted, SA_RIGHT_SAM_OPEN_DOMAIN, "_samr_lookup_domain"))) {
2540 rpcstr_pull(domain_name, q_u->uni_domain.buffer, sizeof(domain_name), q_u->uni_domain.uni_str_len*2, 0);
2544 if (!secrets_fetch_domain_sid(domain_name, &sid)) {
2545 r_u->status = NT_STATUS_NO_SUCH_DOMAIN;
2548 DEBUG(2,("Returning domain sid for domain %s -> %s\n", domain_name, sid_string_static(&sid)));
2550 init_samr_r_lookup_domain(r_u, &sid, r_u->status);
2555 /******************************************************************
2556 makes a SAMR_R_ENUM_DOMAINS structure.
2557 ********************************************************************/
2559 static BOOL make_enum_domains(TALLOC_CTX *ctx, SAM_ENTRY **pp_sam,
2560 UNISTR2 **pp_uni_name, uint32 num_sam_entries, fstring doms[])
2566 DEBUG(5, ("make_enum_domains\n"));
2569 *pp_uni_name = NULL;
2571 if (num_sam_entries == 0)
2574 sam = (SAM_ENTRY *)talloc_zero(ctx, sizeof(SAM_ENTRY)*num_sam_entries);
2575 uni_name = (UNISTR2 *)talloc_zero(ctx, sizeof(UNISTR2)*num_sam_entries);
2577 if (sam == NULL || uni_name == NULL)
2580 for (i = 0; i < num_sam_entries; i++) {
2581 int len = doms[i] != NULL ? strlen(doms[i]) : 0;
2583 init_sam_entry(&sam[i], len, 0);
2584 init_unistr2(&uni_name[i], doms[i], len);
2588 *pp_uni_name = uni_name;
2593 /**********************************************************************
2594 api_samr_enum_domains
2595 **********************************************************************/
2597 NTSTATUS _samr_enum_domains(pipes_struct *p, SAMR_Q_ENUM_DOMAINS *q_u, SAMR_R_ENUM_DOMAINS *r_u)
2599 struct samr_info *info;
2600 uint32 num_entries = 2;
2604 r_u->status = NT_STATUS_OK;
2606 if (!find_policy_by_hnd(p, &q_u->pol, (void**)&info))
2607 return NT_STATUS_INVALID_HANDLE;
2609 if (!NT_STATUS_IS_OK(r_u->status = access_check_samr_function(info->acc_granted, SA_RIGHT_SAM_ENUM_DOMAINS, "_samr_enum_domains"))) {
2613 switch (lp_server_role()) {
2614 case ROLE_DOMAIN_PDC:
2615 case ROLE_DOMAIN_BDC:
2616 name = lp_workgroup();
2619 name = global_myname();
2622 fstrcpy(dom[0],name);
2624 fstrcpy(dom[1],"Builtin");
2626 if (!make_enum_domains(p->mem_ctx, &r_u->sam, &r_u->uni_dom_name, num_entries, dom))
2627 return NT_STATUS_NO_MEMORY;
2629 init_samr_r_enum_domains(r_u, q_u->start_idx + num_entries, num_entries);
2634 /*******************************************************************
2636 ********************************************************************/
2638 NTSTATUS _api_samr_open_alias(pipes_struct *p, SAMR_Q_OPEN_ALIAS *q_u, SAMR_R_OPEN_ALIAS *r_u)
2641 POLICY_HND domain_pol = q_u->dom_pol;
2642 uint32 alias_rid = q_u->rid_alias;
2643 POLICY_HND *alias_pol = &r_u->pol;
2644 struct samr_info *info = NULL;
2645 SEC_DESC *psd = NULL;
2647 uint32 des_access = q_u->access_mask;
2651 r_u->status = NT_STATUS_OK;
2653 /* find the domain policy and get the SID / access bits stored in the domain policy */
2654 if (!get_lsa_policy_samr_sid(p, &domain_pol, &sid, &acc_granted))
2655 return NT_STATUS_INVALID_HANDLE;
2657 if (!NT_STATUS_IS_OK(status = access_check_samr_function(acc_granted, SA_RIGHT_DOMAIN_OPEN_ACCOUNT, "_samr_open_alias"))) {
2661 /* append the alias' RID to it */
2662 if (!sid_append_rid(&sid, alias_rid))
2663 return NT_STATUS_NO_SUCH_USER;
2665 /*check if access can be granted as requested by client. */
2666 samr_make_ali_obj_sd(p->mem_ctx, &psd, &sd_size);
2667 se_map_generic(&des_access,&ali_generic_mapping);
2668 if (!NT_STATUS_IS_OK(status =
2669 access_check_samr_object(psd, p->pipe_user.nt_user_token,
2670 des_access, &acc_granted, "_samr_open_alias"))) {
2675 * we should check if the rid really exist !!!
2679 /* associate the user's SID with the new handle. */
2680 if ((info = get_samr_info_by_sid(&sid)) == NULL)
2681 return NT_STATUS_NO_MEMORY;
2683 info->acc_granted = acc_granted;
2685 /* get a (unique) handle. open a policy on it. */
2686 if (!create_policy_hnd(p, alias_pol, free_samr_info, (void *)info))
2687 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
2692 /*******************************************************************
2694 ********************************************************************/
2696 static BOOL set_user_info_10(const SAM_USER_INFO_10 *id10, DOM_SID *sid)
2698 SAM_ACCOUNT *pwd =NULL;
2703 ret = pdb_getsampwsid(pwd, sid);
2711 DEBUG(5, ("set_user_info_10: NULL id10\n"));
2716 /* FIX ME: check if the value is really changed --metze */
2717 if (!pdb_set_acct_ctrl(pwd, id10->acb_info, PDB_CHANGED)) {
2722 if(!pdb_update_sam_account(pwd)) {
2732 /*******************************************************************
2734 ********************************************************************/
2736 static BOOL set_user_info_12(SAM_USER_INFO_12 *id12, DOM_SID *sid)
2738 SAM_ACCOUNT *pwd = NULL;
2742 if(!pdb_getsampwsid(pwd, sid)) {
2748 DEBUG(2, ("set_user_info_12: id12 is NULL\n"));
2753 if (!pdb_set_lanman_passwd (pwd, id12->lm_pwd, PDB_CHANGED)) {
2757 if (!pdb_set_nt_passwd (pwd, id12->nt_pwd, PDB_CHANGED)) {
2761 if (!pdb_set_pass_changed_now (pwd)) {
2766 if(!pdb_update_sam_account(pwd)) {
2775 /*******************************************************************
2777 ********************************************************************/
2779 static BOOL set_user_info_21(SAM_USER_INFO_21 *id21, DOM_SID *sid)
2781 SAM_ACCOUNT *pwd = NULL;
2784 DEBUG(5, ("set_user_info_21: NULL id21\n"));
2790 if (!pdb_getsampwsid(pwd, sid)) {
2795 copy_id21_to_sam_passwd(pwd, id21);
2798 * The funny part about the previous two calls is
2799 * that pwd still has the password hashes from the
2800 * passdb entry. These have not been updated from
2801 * id21. I don't know if they need to be set. --jerry
2804 /* write the change out */
2805 if(!pdb_update_sam_account(pwd)) {
2815 /*******************************************************************
2817 ********************************************************************/
2819 static BOOL set_user_info_23(SAM_USER_INFO_23 *id23, DOM_SID *sid)
2821 SAM_ACCOUNT *pwd = NULL;
2822 pstring plaintext_buf;
2827 DEBUG(5, ("set_user_info_23: NULL id23\n"));
2833 if (!pdb_getsampwsid(pwd, sid)) {
2838 DEBUG(5, ("Attempting administrator password change (level 23) for user %s\n",
2839 pdb_get_username(pwd)));
2841 acct_ctrl = pdb_get_acct_ctrl(pwd);
2843 if (!decode_pw_buffer((char*)id23->pass, plaintext_buf, 256, &len)) {
2848 if (!pdb_set_plaintext_passwd (pwd, plaintext_buf)) {
2853 copy_id23_to_sam_passwd(pwd, id23);
2855 /* if it's a trust account, don't update /etc/passwd */
2856 if ( (!IS_SAM_UNIX_USER(pwd)) ||
2857 ( (acct_ctrl & ACB_DOMTRUST) == ACB_DOMTRUST ) ||
2858 ( (acct_ctrl & ACB_WSTRUST) == ACB_WSTRUST) ||
2859 ( (acct_ctrl & ACB_SVRTRUST) == ACB_SVRTRUST) ) {
2860 DEBUG(5, ("Changing trust account or non-unix-user password, not updating /etc/passwd\n"));
2862 /* update the UNIX password */
2863 if (lp_unix_password_sync() )
2864 if(!chgpasswd(pdb_get_username(pwd), "", plaintext_buf, True)) {
2870 ZERO_STRUCT(plaintext_buf);
2872 if(!pdb_update_sam_account(pwd)) {
2882 /*******************************************************************
2884 ********************************************************************/
2886 static BOOL set_user_info_pw(char *pass, DOM_SID *sid)
2888 SAM_ACCOUNT *pwd = NULL;
2890 pstring plaintext_buf;
2895 if (!pdb_getsampwsid(pwd, sid)) {
2900 DEBUG(5, ("Attempting administrator password change for user %s\n",
2901 pdb_get_username(pwd)));
2903 acct_ctrl = pdb_get_acct_ctrl(pwd);
2905 ZERO_STRUCT(plaintext_buf);
2907 if (!decode_pw_buffer(pass, plaintext_buf, 256, &len)) {
2912 if (!pdb_set_plaintext_passwd (pwd, plaintext_buf)) {
2917 /* if it's a trust account, don't update /etc/passwd */
2918 if ( (!IS_SAM_UNIX_USER(pwd)) ||
2919 ( (acct_ctrl & ACB_DOMTRUST) == ACB_DOMTRUST ) ||
2920 ( (acct_ctrl & ACB_WSTRUST) == ACB_WSTRUST) ||
2921 ( (acct_ctrl & ACB_SVRTRUST) == ACB_SVRTRUST) ) {
2922 DEBUG(5, ("Changing trust account or non-unix-user password, not updating /etc/passwd\n"));
2924 /* update the UNIX password */
2925 if (lp_unix_password_sync()) {
2926 if(!chgpasswd(pdb_get_username(pwd), "", plaintext_buf, True)) {
2933 ZERO_STRUCT(plaintext_buf);
2935 DEBUG(5,("set_user_info_pw: pdb_update_pwd()\n"));
2937 /* update the SAMBA password */
2938 if(!pdb_update_sam_account(pwd)) {
2948 /*******************************************************************
2949 samr_reply_set_userinfo
2950 ********************************************************************/
2952 NTSTATUS _samr_set_userinfo(pipes_struct *p, SAMR_Q_SET_USERINFO *q_u, SAMR_R_SET_USERINFO *r_u)
2955 POLICY_HND *pol = &q_u->pol;
2956 uint16 switch_value = q_u->switch_value;
2957 SAM_USERINFO_CTR *ctr = q_u->ctr;
2959 uint32 acc_required;
2961 DEBUG(5, ("_samr_set_userinfo: %d\n", __LINE__));
2963 r_u->status = NT_STATUS_OK;
2965 /* find the policy handle. open a policy on it. */
2966 if (!get_lsa_policy_samr_sid(p, pol, &sid, &acc_granted))
2967 return NT_STATUS_INVALID_HANDLE;
2969 acc_required = SA_RIGHT_USER_SET_LOC_COM | SA_RIGHT_USER_SET_ATTRIBUTES; /* This is probably wrong */
2970 if (!NT_STATUS_IS_OK(r_u->status = access_check_samr_function(acc_granted, acc_required, "_samr_set_userinfo"))) {
2974 DEBUG(5, ("_samr_set_userinfo: sid:%s, level:%d\n", sid_string_static(&sid), switch_value));
2977 DEBUG(5, ("_samr_set_userinfo: NULL info level\n"));
2978 return NT_STATUS_INVALID_INFO_CLASS;
2981 /* ok! user info levels (lots: see MSDEV help), off we go... */
2982 switch (switch_value) {
2984 if (!set_user_info_12(ctr->info.id12, &sid))
2985 return NT_STATUS_ACCESS_DENIED;
2989 SamOEMhash(ctr->info.id24->pass, p->session_key, 516);
2991 dump_data(100, (char *)ctr->info.id24->pass, 516);
2993 if (!set_user_info_pw((char *)ctr->info.id24->pass, &sid))
2994 return NT_STATUS_ACCESS_DENIED;
3000 * Currently we don't really know how to unmarshall
3001 * the level 25 struct, and the password encryption
3002 * is different. This is a placeholder for when we
3003 * do understand it. In the meantime just return INVALID
3004 * info level and W2K SP2 drops down to level 23... JRA.
3007 SamOEMhash(ctr->info.id25->pass, p->session_key, 532);
3009 dump_data(100, (char *)ctr->info.id25->pass, 532);
3011 if (!set_user_info_pw(ctr->info.id25->pass, &sid))
3012 return NT_STATUS_ACCESS_DENIED;
3015 return NT_STATUS_INVALID_INFO_CLASS;
3018 SamOEMhash(ctr->info.id23->pass, p->session_key, 516);
3020 dump_data(100, (char *)ctr->info.id23->pass, 516);
3022 if (!set_user_info_23(ctr->info.id23, &sid))
3023 return NT_STATUS_ACCESS_DENIED;
3027 return NT_STATUS_INVALID_INFO_CLASS;
3033 /*******************************************************************
3034 samr_reply_set_userinfo2
3035 ********************************************************************/
3037 NTSTATUS _samr_set_userinfo2(pipes_struct *p, SAMR_Q_SET_USERINFO2 *q_u, SAMR_R_SET_USERINFO2 *r_u)
3040 SAM_USERINFO_CTR *ctr = q_u->ctr;
3041 POLICY_HND *pol = &q_u->pol;
3042 uint16 switch_value = q_u->switch_value;
3044 uint32 acc_required;
3046 DEBUG(5, ("samr_reply_set_userinfo2: %d\n", __LINE__));
3048 r_u->status = NT_STATUS_OK;
3050 /* find the policy handle. open a policy on it. */
3051 if (!get_lsa_policy_samr_sid(p, pol, &sid, &acc_granted))
3052 return NT_STATUS_INVALID_HANDLE;
3054 acc_required = SA_RIGHT_USER_SET_LOC_COM | SA_RIGHT_USER_SET_ATTRIBUTES; /* This is probably wrong */
3055 if (!NT_STATUS_IS_OK(r_u->status = access_check_samr_function(acc_granted, acc_required, "_samr_set_userinfo2"))) {
3059 DEBUG(5, ("samr_reply_set_userinfo2: sid:%s\n", sid_string_static(&sid)));
3062 DEBUG(5, ("samr_reply_set_userinfo2: NULL info level\n"));
3063 return NT_STATUS_INVALID_INFO_CLASS;
3066 switch_value=ctr->switch_value;
3068 /* ok! user info levels (lots: see MSDEV help), off we go... */
3069 switch (switch_value) {
3071 if (!set_user_info_21(ctr->info.id21, &sid))
3072 return NT_STATUS_ACCESS_DENIED;
3075 if (!set_user_info_10(ctr->info.id10, &sid))
3076 return NT_STATUS_ACCESS_DENIED;
3079 /* Used by AS/U JRA. */
3080 if (!set_user_info_12(ctr->info.id12, &sid))
3081 return NT_STATUS_ACCESS_DENIED;
3084 return NT_STATUS_INVALID_INFO_CLASS;
3090 /*********************************************************************
3091 _samr_query_aliasmem
3092 *********************************************************************/
3094 NTSTATUS _samr_query_useraliases(pipes_struct *p, SAMR_Q_QUERY_USERALIASES *q_u, SAMR_R_QUERY_USERALIASES *r_u)
3096 int num_groups = 0, tmp_num_groups=0;
3097 uint32 *rids=NULL, *new_rids=NULL, *tmp_rids=NULL;
3098 struct samr_info *info = NULL;
3104 /* until i see a real useraliases query, we fack one up */
3106 /* I have seen one, JFM 2/12/2001 */
3108 * Explanation of what this call does:
3109 * for all the SID given in the request:
3110 * return a list of alias (local groups)
3111 * that have those SID as members.
3113 * and that's the alias in the domain specified
3114 * in the policy_handle
3116 * if the policy handle is on an incorrect sid
3117 * for example a user's sid
3118 * we should reply NT_STATUS_OBJECT_TYPE_MISMATCH
3121 r_u->status = NT_STATUS_OK;
3123 DEBUG(5,("_samr_query_useraliases: %d\n", __LINE__));
3125 /* find the policy handle. open a policy on it. */
3126 if (!find_policy_by_hnd(p, &q_u->pol, (void **)&info))
3127 return NT_STATUS_INVALID_HANDLE;
3129 ntstatus1 = access_check_samr_function(info->acc_granted, SA_RIGHT_DOMAIN_LOOKUP_ALIAS_BY_MEM, "_samr_query_useraliases");
3130 ntstatus2 = access_check_samr_function(info->acc_granted, SA_RIGHT_DOMAIN_OPEN_ACCOUNT, "_samr_query_useraliases");
3132 if (!NT_STATUS_IS_OK(ntstatus1) || !NT_STATUS_IS_OK(ntstatus2)) {
3133 if (!(NT_STATUS_EQUAL(ntstatus1,NT_STATUS_ACCESS_DENIED) && NT_STATUS_IS_OK(ntstatus2)) &&
3134 !(NT_STATUS_EQUAL(ntstatus1,NT_STATUS_ACCESS_DENIED) && NT_STATUS_IS_OK(ntstatus1))) {
3135 return (NT_STATUS_IS_OK(ntstatus1)) ? ntstatus2 : ntstatus1;
3139 if (!sid_check_is_domain(&info->sid) &&
3140 !sid_check_is_builtin(&info->sid))
3141 return NT_STATUS_OBJECT_TYPE_MISMATCH;
3144 for (i=0; i<q_u->num_sids1; i++) {
3146 r_u->status=get_alias_user_groups(p->mem_ctx, &info->sid, &tmp_num_groups, &tmp_rids, &(q_u->sid[i].sid));
3149 * if there is an error, we just continue as
3150 * it can be an unfound user or group
3152 if (!NT_STATUS_IS_OK(r_u->status)) {
3153 DEBUG(10,("_samr_query_useraliases: an error occured while getting groups\n"));
3157 if (tmp_num_groups==0) {
3158 DEBUG(10,("_samr_query_useraliases: no groups found\n"));
3162 new_rids=(uint32 *)talloc_realloc(p->mem_ctx, rids, (num_groups+tmp_num_groups)*sizeof(uint32));
3163 if (new_rids==NULL) {
3164 DEBUG(0,("_samr_query_useraliases: could not realloc memory\n"));
3165 return NT_STATUS_NO_MEMORY;
3169 for (j=0; j<tmp_num_groups; j++)
3170 rids[j+num_groups]=tmp_rids[j];
3172 safe_free(tmp_rids);
3174 num_groups+=tmp_num_groups;
3177 init_samr_r_query_useraliases(r_u, num_groups, rids, NT_STATUS_OK);
3178 return NT_STATUS_OK;
3181 /*********************************************************************
3182 _samr_query_aliasmem
3183 *********************************************************************/
3185 NTSTATUS _samr_query_aliasmem(pipes_struct *p, SAMR_Q_QUERY_ALIASMEM *q_u, SAMR_R_QUERY_ALIASMEM *r_u)
3197 fstring alias_sid_str;
3200 SAM_ACCOUNT *sam_user = NULL;
3204 /* find the policy handle. open a policy on it. */
3205 if (!get_lsa_policy_samr_sid(p, &q_u->alias_pol, &alias_sid, &acc_granted))
3206 return NT_STATUS_INVALID_HANDLE;
3208 if (!NT_STATUS_IS_OK(r_u->status =
3209 access_check_samr_function(acc_granted, SA_RIGHT_ALIAS_GET_MEMBERS, "_samr_query_aliasmem"))) {
3213 sid_copy(&als_sid, &alias_sid);
3214 sid_to_string(alias_sid_str, &alias_sid);
3215 sid_split_rid(&alias_sid, &alias_rid);
3217 DEBUG(10, ("sid is %s\n", alias_sid_str));
3219 if (sid_equal(&alias_sid, &global_sid_Builtin)) {
3220 DEBUG(10, ("lookup on Builtin SID (S-1-5-32)\n"));
3221 if(!get_builtin_group_from_sid(als_sid, &map, MAPPING_WITHOUT_PRIV))
3222 return NT_STATUS_NO_SUCH_ALIAS;
3224 if (sid_equal(&alias_sid, get_global_sam_sid())) {
3225 DEBUG(10, ("lookup on Server SID\n"));
3226 if(!get_local_group_from_sid(als_sid, &map, MAPPING_WITHOUT_PRIV))
3227 return NT_STATUS_NO_SUCH_ALIAS;
3231 if(!get_uid_list_of_group(map.gid, &uid, &num_uids))
3232 return NT_STATUS_NO_SUCH_ALIAS;
3234 DEBUG(10, ("sid is %s\n", alias_sid_str));
3235 sid = (DOM_SID2 *)talloc_zero(p->mem_ctx, sizeof(DOM_SID2) * num_uids);
3236 if (num_uids!=0 && sid == NULL)
3237 return NT_STATUS_NO_MEMORY;
3239 for (i = 0; i < num_uids; i++) {
3240 struct passwd *pass;
3243 sid_copy(&temp_sid, get_global_sam_sid());
3245 pass = getpwuid_alloc(uid[i]);
3246 if (!pass) continue;
3248 if (!NT_STATUS_IS_OK(pdb_init_sam(&sam_user))) {
3254 check = pdb_getsampwnam(sam_user, pass->pw_name);
3257 if (check != True) {
3258 pdb_free_sam(&sam_user);
3263 rid = pdb_get_user_rid(sam_user);
3265 pdb_free_sam(&sam_user);
3270 pdb_free_sam(&sam_user);
3273 sid_append_rid(&temp_sid, rid);
3275 init_dom_sid2(&sid[i], &temp_sid);
3278 DEBUG(10, ("sid is %s\n", alias_sid_str));
3279 init_samr_r_query_aliasmem(r_u, num_uids, sid, NT_STATUS_OK);
3281 return NT_STATUS_OK;
3284 /*********************************************************************
3285 _samr_query_groupmem
3286 *********************************************************************/
3288 NTSTATUS _samr_query_groupmem(pipes_struct *p, SAMR_Q_QUERY_GROUPMEM *q_u, SAMR_R_QUERY_GROUPMEM *r_u)
3294 fstring group_sid_str;
3302 SAM_ACCOUNT *sam_user = NULL;
3306 /* find the policy handle. open a policy on it. */
3307 if (!get_lsa_policy_samr_sid(p, &q_u->group_pol, &group_sid, &acc_granted))
3308 return NT_STATUS_INVALID_HANDLE;
3310 if (!NT_STATUS_IS_OK(r_u->status = access_check_samr_function(acc_granted, SA_RIGHT_GROUP_GET_MEMBERS, "_samr_query_groupmem"))) {
3314 /* todo: change to use sid_compare_front */
3316 sid_split_rid(&group_sid, &group_rid);
3317 sid_to_string(group_sid_str, &group_sid);
3318 DEBUG(10, ("sid is %s\n", group_sid_str));
3320 /* can we get a query for an SID outside our domain ? */
3321 if (!sid_equal(&group_sid, get_global_sam_sid()))
3322 return NT_STATUS_NO_SUCH_GROUP;
3324 sid_append_rid(&group_sid, group_rid);
3325 DEBUG(10, ("lookup on Domain SID\n"));
3327 if(!get_domain_group_from_sid(group_sid, &map, MAPPING_WITHOUT_PRIV))
3328 return NT_STATUS_NO_SUCH_GROUP;
3330 if(!get_uid_list_of_group(map.gid, &uid, &num_uids))
3331 return NT_STATUS_NO_SUCH_GROUP;
3333 rid=talloc_zero(p->mem_ctx, sizeof(uint32)*num_uids);
3334 attr=talloc_zero(p->mem_ctx, sizeof(uint32)*num_uids);
3336 if (num_uids!=0 && (rid==NULL || attr==NULL))
3337 return NT_STATUS_NO_MEMORY;
3339 for (i=0; i<num_uids; i++) {
3340 struct passwd *pass;
3343 pass = getpwuid_alloc(uid[i]);
3344 if (!pass) continue;
3346 if (!NT_STATUS_IS_OK(pdb_init_sam(&sam_user))) {
3352 check = pdb_getsampwnam(sam_user, pass->pw_name);
3355 if (check != True) {
3356 pdb_free_sam(&sam_user);
3361 urid = pdb_get_user_rid(sam_user);
3363 pdb_free_sam(&sam_user);
3368 pdb_free_sam(&sam_user);
3372 attr[i] = SID_NAME_USER;
3375 init_samr_r_query_groupmem(r_u, num_uids, rid, attr, NT_STATUS_OK);
3377 return NT_STATUS_OK;
3380 /*********************************************************************
3382 *********************************************************************/
3384 NTSTATUS _samr_add_aliasmem(pipes_struct *p, SAMR_Q_ADD_ALIASMEM *q_u, SAMR_R_ADD_ALIASMEM *r_u)
3387 fstring alias_sid_str;
3394 SAM_ACCOUNT *sam_user = NULL;
3398 /* Find the policy handle. Open a policy on it. */
3399 if (!get_lsa_policy_samr_sid(p, &q_u->alias_pol, &alias_sid, &acc_granted))
3400 return NT_STATUS_INVALID_HANDLE;
3402 if (!NT_STATUS_IS_OK(r_u->status = access_check_samr_function(acc_granted, SA_RIGHT_ALIAS_ADD_MEMBER, "_samr_add_aliasmem"))) {
3406 sid_to_string(alias_sid_str, &alias_sid);
3407 DEBUG(10, ("sid is %s\n", alias_sid_str));
3409 if (sid_compare(&alias_sid, get_global_sam_sid())>0) {
3410 DEBUG(10, ("adding member on Server SID\n"));
3411 if(!get_local_group_from_sid(alias_sid, &map, MAPPING_WITHOUT_PRIV))
3412 return NT_STATUS_NO_SUCH_ALIAS;
3415 if (sid_compare(&alias_sid, &global_sid_Builtin)>0) {
3416 DEBUG(10, ("adding member on BUILTIN SID\n"));
3417 if( !get_local_group_from_sid(alias_sid, &map, MAPPING_WITHOUT_PRIV))
3418 return NT_STATUS_NO_SUCH_ALIAS;
3421 return NT_STATUS_NO_SUCH_ALIAS;
3424 ret = pdb_init_sam(&sam_user);
3425 if (!NT_STATUS_IS_OK(ret))
3428 check = pdb_getsampwsid(sam_user, &q_u->sid.sid);
3430 if (check != True) {
3431 pdb_free_sam(&sam_user);
3432 return NT_STATUS_NO_SUCH_USER;
3435 uid = pdb_get_uid(sam_user);
3437 pdb_free_sam(&sam_user);
3438 return NT_STATUS_NO_SUCH_USER;
3441 pdb_free_sam(&sam_user);
3443 if ((pwd=getpwuid_alloc(uid)) == NULL) {
3444 return NT_STATUS_NO_SUCH_USER;
3447 if ((grp=getgrgid(map.gid)) == NULL) {
3449 return NT_STATUS_NO_SUCH_ALIAS;
3452 /* we need to copy the name otherwise it's overloaded in user_in_group_list */
3453 fstrcpy(grp_name, grp->gr_name);
3455 /* if the user is already in the group */
3456 if(user_in_unix_group_list(pwd->pw_name, grp_name)) {
3458 return NT_STATUS_MEMBER_IN_ALIAS;
3462 * ok, the group exist, the user exist, the user is not in the group,
3463 * we can (finally) add it to the group !
3465 smb_add_user_group(grp_name, pwd->pw_name);
3467 /* check if the user has been added then ... */
3468 if(!user_in_unix_group_list(pwd->pw_name, grp_name)) {
3470 return NT_STATUS_MEMBER_NOT_IN_ALIAS; /* don't know what to reply else */
3474 return NT_STATUS_OK;
3477 /*********************************************************************
3479 *********************************************************************/
3481 NTSTATUS _samr_del_aliasmem(pipes_struct *p, SAMR_Q_DEL_ALIASMEM *q_u, SAMR_R_DEL_ALIASMEM *r_u)
3484 fstring alias_sid_str;
3488 SAM_ACCOUNT *sam_pass=NULL;
3491 /* Find the policy handle. Open a policy on it. */
3492 if (!get_lsa_policy_samr_sid(p, &q_u->alias_pol, &alias_sid, &acc_granted))
3493 return NT_STATUS_INVALID_HANDLE;
3495 if (!NT_STATUS_IS_OK(r_u->status = access_check_samr_function(acc_granted, SA_RIGHT_ALIAS_REMOVE_MEMBER, "_samr_del_aliasmem"))) {
3499 sid_to_string(alias_sid_str, &alias_sid);
3500 DEBUG(10, ("_samr_del_aliasmem:sid is %s\n", alias_sid_str));
3502 if (!sid_check_is_in_our_domain(&alias_sid) &&
3503 !sid_check_is_in_builtin(&alias_sid)) {
3504 DEBUG(10, ("_samr_del_aliasmem:invalid alias group\n"));
3505 return NT_STATUS_NO_SUCH_ALIAS;
3508 if( !get_local_group_from_sid(alias_sid, &map, MAPPING_WITHOUT_PRIV))
3509 return NT_STATUS_NO_SUCH_ALIAS;
3511 if ((grp=getgrgid(map.gid)) == NULL)
3512 return NT_STATUS_NO_SUCH_ALIAS;
3514 /* we need to copy the name otherwise it's overloaded in user_in_unix_group_list */
3515 fstrcpy(grp_name, grp->gr_name);
3517 /* check if the user exists before trying to remove it from the group */
3518 pdb_init_sam(&sam_pass);
3519 if(!pdb_getsampwsid(sam_pass, &q_u->sid.sid)) {
3520 DEBUG(5,("_samr_del_aliasmem:User %s doesn't exist.\n", pdb_get_username(sam_pass)));
3521 pdb_free_sam(&sam_pass);
3522 return NT_STATUS_NO_SUCH_USER;
3525 /* if the user is not in the group */
3526 if(!user_in_unix_group_list(pdb_get_username(sam_pass), grp_name)) {
3527 pdb_free_sam(&sam_pass);
3528 return NT_STATUS_MEMBER_IN_ALIAS;
3531 smb_delete_user_group(grp_name, pdb_get_username(sam_pass));
3533 /* check if the user has been removed then ... */
3534 if(user_in_unix_group_list(pdb_get_username(sam_pass), grp_name)) {
3535 pdb_free_sam(&sam_pass);
3536 return NT_STATUS_MEMBER_NOT_IN_ALIAS; /* don't know what to reply else */
3539 pdb_free_sam(&sam_pass);
3540 return NT_STATUS_OK;
3543 /*********************************************************************
3545 *********************************************************************/
3547 NTSTATUS _samr_add_groupmem(pipes_struct *p, SAMR_Q_ADD_GROUPMEM *q_u, SAMR_R_ADD_GROUPMEM *r_u)
3551 fstring group_sid_str;
3558 SAM_ACCOUNT *sam_user=NULL;
3562 /* Find the policy handle. Open a policy on it. */
3563 if (!get_lsa_policy_samr_sid(p, &q_u->pol, &group_sid, &acc_granted))
3564 return NT_STATUS_INVALID_HANDLE;
3566 if (!NT_STATUS_IS_OK(r_u->status = access_check_samr_function(acc_granted, SA_RIGHT_GROUP_ADD_MEMBER, "_samr_add_groupmem"))) {
3570 sid_to_string(group_sid_str, &group_sid);
3571 DEBUG(10, ("sid is %s\n", group_sid_str));
3573 if (sid_compare(&group_sid, get_global_sam_sid())<=0)
3574 return NT_STATUS_NO_SUCH_GROUP;
3576 DEBUG(10, ("lookup on Domain SID\n"));
3578 if(!get_domain_group_from_sid(group_sid, &map, MAPPING_WITHOUT_PRIV))
3579 return NT_STATUS_NO_SUCH_GROUP;
3581 sid_copy(&user_sid, get_global_sam_sid());
3582 sid_append_rid(&user_sid, q_u->rid);
3584 ret = pdb_init_sam(&sam_user);
3585 if (!NT_STATUS_IS_OK(ret))
3588 check = pdb_getsampwsid(sam_user, &user_sid);
3590 if (check != True) {
3591 pdb_free_sam(&sam_user);
3592 return NT_STATUS_NO_SUCH_USER;
3595 uid = pdb_get_uid(sam_user);
3597 pdb_free_sam(&sam_user);
3598 return NT_STATUS_NO_SUCH_USER;
3601 pdb_free_sam(&sam_user);
3603 if ((pwd=getpwuid_alloc(uid)) == NULL) {
3604 return NT_STATUS_NO_SUCH_USER;
3607 if ((grp=getgrgid(map.gid)) == NULL) {
3609 return NT_STATUS_NO_SUCH_GROUP;
3612 /* we need to copy the name otherwise it's overloaded in user_in_unix_group_list */
3613 fstrcpy(grp_name, grp->gr_name);
3615 /* if the user is already in the group */
3616 if(user_in_unix_group_list(pwd->pw_name, grp_name)) {
3618 return NT_STATUS_MEMBER_IN_GROUP;
3622 * ok, the group exist, the user exist, the user is not in the group,
3624 * we can (finally) add it to the group !
3627 smb_add_user_group(grp_name, pwd->pw_name);
3629 /* check if the user has been added then ... */
3630 if(!user_in_unix_group_list(pwd->pw_name, grp_name)) {
3632 return NT_STATUS_MEMBER_NOT_IN_GROUP; /* don't know what to reply else */
3636 return NT_STATUS_OK;
3639 /*********************************************************************
3641 *********************************************************************/
3643 NTSTATUS _samr_del_groupmem(pipes_struct *p, SAMR_Q_DEL_GROUPMEM *q_u, SAMR_R_DEL_GROUPMEM *r_u)
3647 SAM_ACCOUNT *sam_pass=NULL;
3654 * delete the group member named q_u->rid
3655 * who is a member of the sid associated with the handle
3656 * the rid is a user's rid as the group is a domain group.
3659 /* Find the policy handle. Open a policy on it. */
3660 if (!get_lsa_policy_samr_sid(p, &q_u->pol, &group_sid, &acc_granted))
3661 return NT_STATUS_INVALID_HANDLE;
3663 if (!NT_STATUS_IS_OK(r_u->status = access_check_samr_function(acc_granted, SA_RIGHT_GROUP_REMOVE_MEMBER, "_samr_del_groupmem"))) {
3667 if (!sid_check_is_in_our_domain(&group_sid))
3668 return NT_STATUS_NO_SUCH_GROUP;
3670 sid_copy(&user_sid, get_global_sam_sid());
3671 sid_append_rid(&user_sid, q_u->rid);
3673 if (!get_domain_group_from_sid(group_sid, &map, MAPPING_WITHOUT_PRIV))
3674 return NT_STATUS_NO_SUCH_GROUP;
3676 if ((grp=getgrgid(map.gid)) == NULL)
3677 return NT_STATUS_NO_SUCH_GROUP;
3679 /* we need to copy the name otherwise it's overloaded in user_in_group_list */
3680 fstrcpy(grp_name, grp->gr_name);
3682 /* check if the user exists before trying to remove it from the group */
3683 pdb_init_sam(&sam_pass);
3684 if (!pdb_getsampwsid(sam_pass, &user_sid)) {
3685 DEBUG(5,("User %s doesn't exist.\n", pdb_get_username(sam_pass)));
3686 pdb_free_sam(&sam_pass);
3687 return NT_STATUS_NO_SUCH_USER;
3690 /* if the user is not in the group */
3691 if (!user_in_unix_group_list(pdb_get_username(sam_pass), grp_name)) {
3692 pdb_free_sam(&sam_pass);
3693 return NT_STATUS_MEMBER_NOT_IN_GROUP;
3696 smb_delete_user_group(grp_name, pdb_get_username(sam_pass));
3698 /* check if the user has been removed then ... */
3699 if (user_in_unix_group_list(pdb_get_username(sam_pass), grp_name)) {
3700 pdb_free_sam(&sam_pass);
3701 return NT_STATUS_ACCESS_DENIED; /* don't know what to reply else */
3704 pdb_free_sam(&sam_pass);
3705 return NT_STATUS_OK;
3709 /****************************************************************************
3710 Delete a UNIX user on demand.
3711 ****************************************************************************/
3713 static int smb_delete_user(const char *unix_user)
3718 pstrcpy(del_script, lp_deluser_script());
3721 all_string_sub(del_script, "%u", unix_user, sizeof(pstring));
3722 ret = smbrun(del_script,NULL);
3723 DEBUG(3,("smb_delete_user: Running the command `%s' gave %d\n",del_script,ret));
3727 /*********************************************************************
3728 _samr_delete_dom_user
3729 *********************************************************************/
3731 NTSTATUS _samr_delete_dom_user(pipes_struct *p, SAMR_Q_DELETE_DOM_USER *q_u, SAMR_R_DELETE_DOM_USER *r_u )
3734 SAM_ACCOUNT *sam_pass=NULL;
3737 DEBUG(5, ("_samr_delete_dom_user: %d\n", __LINE__));
3739 /* Find the policy handle. Open a policy on it. */
3740 if (!get_lsa_policy_samr_sid(p, &q_u->user_pol, &user_sid, &acc_granted))
3741 return NT_STATUS_INVALID_HANDLE;
3743 if (!NT_STATUS_IS_OK(r_u->status = access_check_samr_function(acc_granted, STD_RIGHT_DELETE_ACCESS, "_samr_delete_dom_user"))) {
3747 if (!sid_check_is_in_our_domain(&user_sid))
3748 return NT_STATUS_CANNOT_DELETE;
3750 /* check if the user exists before trying to delete */
3751 pdb_init_sam(&sam_pass);
3752 if(!pdb_getsampwsid(sam_pass, &user_sid)) {
3753 DEBUG(5,("_samr_delete_dom_user:User %s doesn't exist.\n", pdb_get_username(sam_pass)));
3754 pdb_free_sam(&sam_pass);
3755 return NT_STATUS_NO_SUCH_USER;
3758 /* delete the unix side */
3760 * note: we don't check if the delete really happened
3761 * as the script is not necessary present
3762 * and maybe the sysadmin doesn't want to delete the unix side
3764 smb_delete_user(pdb_get_username(sam_pass));
3766 /* and delete the samba side */
3767 if (!pdb_delete_sam_account(sam_pass)) {
3768 DEBUG(5,("_samr_delete_dom_user:Failed to delete entry for user %s.\n", pdb_get_username(sam_pass)));
3769 pdb_free_sam(&sam_pass);
3770 return NT_STATUS_CANNOT_DELETE;
3773 pdb_free_sam(&sam_pass);
3775 if (!close_policy_hnd(p, &q_u->user_pol))
3776 return NT_STATUS_OBJECT_NAME_INVALID;
3778 return NT_STATUS_OK;
3781 /*********************************************************************
3782 _samr_delete_dom_group
3783 *********************************************************************/
3785 NTSTATUS _samr_delete_dom_group(pipes_struct *p, SAMR_Q_DELETE_DOM_GROUP *q_u, SAMR_R_DELETE_DOM_GROUP *r_u)
3790 fstring group_sid_str;
3796 DEBUG(5, ("samr_delete_dom_group: %d\n", __LINE__));
3798 /* Find the policy handle. Open a policy on it. */
3799 if (!get_lsa_policy_samr_sid(p, &q_u->group_pol, &group_sid, &acc_granted))
3800 return NT_STATUS_INVALID_HANDLE;
3802 if (!NT_STATUS_IS_OK(r_u->status = access_check_samr_function(acc_granted, STD_RIGHT_DELETE_ACCESS, "_samr_delete_dom_group"))) {
3806 sid_copy(&dom_sid, &group_sid);
3807 sid_to_string(group_sid_str, &dom_sid);
3808 sid_split_rid(&dom_sid, &group_rid);
3810 DEBUG(10, ("sid is %s\n", group_sid_str));
3812 /* we check if it's our SID before deleting */
3813 if (!sid_equal(&dom_sid, get_global_sam_sid()))
3814 return NT_STATUS_NO_SUCH_GROUP;
3816 DEBUG(10, ("lookup on Domain SID\n"));
3818 if(!get_domain_group_from_sid(group_sid, &map, MAPPING_WITHOUT_PRIV))
3819 return NT_STATUS_NO_SUCH_GROUP;
3823 /* check if group really exists */
3824 if ( (grp=getgrgid(gid)) == NULL)
3825 return NT_STATUS_NO_SUCH_GROUP;
3827 /* we can delete the UNIX group */
3828 smb_delete_group(grp->gr_name);
3830 /* check if the group has been successfully deleted */
3831 if ( (grp=getgrgid(gid)) != NULL)
3832 return NT_STATUS_ACCESS_DENIED;
3834 if(!pdb_delete_group_mapping_entry(group_sid))
3835 return NT_STATUS_ACCESS_DENIED;
3837 if (!close_policy_hnd(p, &q_u->group_pol))
3838 return NT_STATUS_OBJECT_NAME_INVALID;
3840 return NT_STATUS_OK;
3843 /*********************************************************************
3844 _samr_delete_dom_alias
3845 *********************************************************************/
3847 NTSTATUS _samr_delete_dom_alias(pipes_struct *p, SAMR_Q_DELETE_DOM_ALIAS *q_u, SAMR_R_DELETE_DOM_ALIAS *r_u)
3852 fstring alias_sid_str;
3858 DEBUG(5, ("_samr_delete_dom_alias: %d\n", __LINE__));
3860 /* Find the policy handle. Open a policy on it. */
3861 if (!get_lsa_policy_samr_sid(p, &q_u->alias_pol, &alias_sid, &acc_granted))
3862 return NT_STATUS_INVALID_HANDLE;
3864 if (!NT_STATUS_IS_OK(r_u->status = access_check_samr_function(acc_granted, STD_RIGHT_DELETE_ACCESS, "_samr_delete_dom_alias"))) {
3868 sid_copy(&dom_sid, &alias_sid);
3869 sid_to_string(alias_sid_str, &dom_sid);
3870 sid_split_rid(&dom_sid, &alias_rid);
3872 DEBUG(10, ("sid is %s\n", alias_sid_str));
3874 /* we check if it's our SID before deleting */
3875 if (!sid_equal(&dom_sid, get_global_sam_sid()))
3876 return NT_STATUS_NO_SUCH_ALIAS;
3878 DEBUG(10, ("lookup on Local SID\n"));
3880 if(!get_local_group_from_sid(alias_sid, &map, MAPPING_WITHOUT_PRIV))
3881 return NT_STATUS_NO_SUCH_ALIAS;
3885 /* check if group really exists */
3886 if ( (grp=getgrgid(gid)) == NULL)
3887 return NT_STATUS_NO_SUCH_ALIAS;
3889 /* we can delete the UNIX group */
3890 smb_delete_group(grp->gr_name);
3892 /* check if the group has been successfully deleted */
3893 if ( (grp=getgrgid(gid)) != NULL)
3894 return NT_STATUS_ACCESS_DENIED;
3896 /* don't check if we removed it as it could be an un-mapped group */
3897 pdb_delete_group_mapping_entry(alias_sid);
3899 if (!close_policy_hnd(p, &q_u->alias_pol))
3900 return NT_STATUS_OBJECT_NAME_INVALID;
3902 return NT_STATUS_OK;
3905 /*********************************************************************
3906 _samr_create_dom_group
3907 *********************************************************************/
3909 NTSTATUS _samr_create_dom_group(pipes_struct *p, SAMR_Q_CREATE_DOM_GROUP *q_u, SAMR_R_CREATE_DOM_GROUP *r_u)
3916 struct samr_info *info;
3917 PRIVILEGE_SET priv_set;
3921 init_privilege(&priv_set);
3923 /* Find the policy handle. Open a policy on it. */
3924 if (!get_lsa_policy_samr_sid(p, &q_u->pol, &dom_sid, &acc_granted))
3925 return NT_STATUS_INVALID_HANDLE;
3927 if (!NT_STATUS_IS_OK(r_u->status = access_check_samr_function(acc_granted, SA_RIGHT_DOMAIN_CREATE_GROUP, "_samr_create_dom_group"))) {
3931 if (!sid_equal(&dom_sid, get_global_sam_sid()))
3932 return NT_STATUS_ACCESS_DENIED;
3934 /* TODO: check if allowed to create group and add a become_root/unbecome_root pair.*/
3936 unistr2_to_ascii(name, &q_u->uni_acct_desc, sizeof(name)-1);
3938 /* check if group already exist */
3939 if ((grp=getgrnam(name)) != NULL)
3940 return NT_STATUS_GROUP_EXISTS;
3942 /* we can create the UNIX group */
3943 if (smb_create_group(name, &gid) != 0)
3944 return NT_STATUS_ACCESS_DENIED;
3946 /* check if the group has been successfully created */
3947 if ((grp=getgrgid(gid)) == NULL)
3948 return NT_STATUS_ACCESS_DENIED;
3950 r_u->rid=pdb_gid_to_group_rid(grp->gr_gid);
3952 /* add the group to the mapping table */
3953 sid_copy(&info_sid, get_global_sam_sid());
3954 sid_append_rid(&info_sid, r_u->rid);
3955 sid_to_string(sid_string, &info_sid);
3957 if(!add_initial_entry(grp->gr_gid, sid_string, SID_NAME_DOM_GRP, name, NULL, priv_set, PR_ACCESS_FROM_NETWORK))
3958 return NT_STATUS_ACCESS_DENIED;
3960 if ((info = get_samr_info_by_sid(&info_sid)) == NULL)
3961 return NT_STATUS_NO_MEMORY;
3963 /* get a (unique) handle. open a policy on it. */
3964 if (!create_policy_hnd(p, &r_u->pol, free_samr_info, (void *)info))
3965 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
3967 return NT_STATUS_OK;
3970 /*********************************************************************
3971 _samr_create_dom_alias
3972 *********************************************************************/
3974 NTSTATUS _samr_create_dom_alias(pipes_struct *p, SAMR_Q_CREATE_DOM_ALIAS *q_u, SAMR_R_CREATE_DOM_ALIAS *r_u)
3981 struct samr_info *info;
3982 PRIVILEGE_SET priv_set;
3986 init_privilege(&priv_set);
3988 /* Find the policy handle. Open a policy on it. */
3989 if (!get_lsa_policy_samr_sid(p, &q_u->dom_pol, &dom_sid, &acc_granted))
3990 return NT_STATUS_INVALID_HANDLE;
3992 if (!NT_STATUS_IS_OK(r_u->status = access_check_samr_function(acc_granted, SA_RIGHT_DOMAIN_CREATE_ALIAS, "_samr_create_alias"))) {
3996 if (!sid_equal(&dom_sid, get_global_sam_sid()))
3997 return NT_STATUS_ACCESS_DENIED;
3999 /* TODO: check if allowed to create group and add a become_root/unbecome_root pair.*/
4001 unistr2_to_ascii(name, &q_u->uni_acct_desc, sizeof(name)-1);
4003 /* check if group already exists */
4004 if ( (grp=getgrnam(name)) != NULL)
4005 return NT_STATUS_GROUP_EXISTS;
4007 /* we can create the UNIX group */
4008 if (smb_create_group(name, &gid) != 0)
4009 return NT_STATUS_ACCESS_DENIED;
4011 /* check if the group has been successfully created */
4012 if ((grp=getgrgid(gid)) == NULL)
4013 return NT_STATUS_ACCESS_DENIED;
4015 r_u->rid=pdb_gid_to_group_rid(grp->gr_gid);
4017 sid_copy(&info_sid, get_global_sam_sid());
4018 sid_append_rid(&info_sid, r_u->rid);
4019 sid_to_string(sid_string, &info_sid);
4021 /* add the group to the mapping table */
4022 if(!add_initial_entry(grp->gr_gid, sid_string, SID_NAME_ALIAS, name, NULL, priv_set, PR_ACCESS_FROM_NETWORK))
4023 return NT_STATUS_ACCESS_DENIED;
4025 if ((info = get_samr_info_by_sid(&info_sid)) == NULL)
4026 return NT_STATUS_NO_MEMORY;
4028 /* get a (unique) handle. open a policy on it. */
4029 if (!create_policy_hnd(p, &r_u->alias_pol, free_samr_info, (void *)info))
4030 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
4032 return NT_STATUS_OK;
4035 /*********************************************************************
4036 _samr_query_groupinfo
4038 sends the name/comment pair of a domain group
4039 level 1 send also the number of users of that group
4040 *********************************************************************/
4042 NTSTATUS _samr_query_groupinfo(pipes_struct *p, SAMR_Q_QUERY_GROUPINFO *q_u, SAMR_R_QUERY_GROUPINFO *r_u)
4048 GROUP_INFO_CTR *ctr;
4051 if (!get_lsa_policy_samr_sid(p, &q_u->pol, &group_sid, &acc_granted))
4052 return NT_STATUS_INVALID_HANDLE;
4054 if (!NT_STATUS_IS_OK(r_u->status = access_check_samr_function(acc_granted, SA_RIGHT_GROUP_LOOKUP_INFO, "_samr_query_groupinfo"))) {
4058 if (!get_domain_group_from_sid(group_sid, &map, MAPPING_WITHOUT_PRIV))
4059 return NT_STATUS_INVALID_HANDLE;
4061 ctr=(GROUP_INFO_CTR *)talloc_zero(p->mem_ctx, sizeof(GROUP_INFO_CTR));
4063 return NT_STATUS_NO_MEMORY;
4065 switch (q_u->switch_level) {
4067 ctr->switch_value1 = 1;
4068 if(!get_uid_list_of_group(map.gid, &uid, &num_uids))
4069 return NT_STATUS_NO_SUCH_GROUP;
4070 init_samr_group_info1(&ctr->group.info1, map.nt_name, map.comment, num_uids);
4074 ctr->switch_value1 = 3;
4075 init_samr_group_info3(&ctr->group.info3);
4078 ctr->switch_value1 = 4;
4079 init_samr_group_info4(&ctr->group.info4, map.comment);
4082 return NT_STATUS_INVALID_INFO_CLASS;
4085 init_samr_r_query_groupinfo(r_u, ctr, NT_STATUS_OK);
4087 return NT_STATUS_OK;
4090 /*********************************************************************
4093 update a domain group's comment.
4094 *********************************************************************/
4096 NTSTATUS _samr_set_groupinfo(pipes_struct *p, SAMR_Q_SET_GROUPINFO *q_u, SAMR_R_SET_GROUPINFO *r_u)
4100 GROUP_INFO_CTR *ctr;
4103 if (!get_lsa_policy_samr_sid(p, &q_u->pol, &group_sid, &acc_granted))
4104 return NT_STATUS_INVALID_HANDLE;
4106 if (!NT_STATUS_IS_OK(r_u->status = access_check_samr_function(acc_granted, SA_RIGHT_GROUP_SET_INFO, "_samr_set_groupinfo"))) {
4110 if (!get_domain_group_from_sid(group_sid, &map, MAPPING_WITH_PRIV))
4111 return NT_STATUS_NO_SUCH_GROUP;
4115 switch (ctr->switch_value1) {
4117 unistr2_to_ascii(map.comment, &(ctr->group.info1.uni_acct_desc), sizeof(map.comment)-1);
4120 unistr2_to_ascii(map.comment, &(ctr->group.info4.uni_acct_desc), sizeof(map.comment)-1);
4123 free_privilege(&map.priv_set);
4124 return NT_STATUS_INVALID_INFO_CLASS;
4127 if(!pdb_update_group_mapping_entry(&map)) {
4128 free_privilege(&map.priv_set);
4129 return NT_STATUS_NO_SUCH_GROUP;
4132 free_privilege(&map.priv_set);
4134 return NT_STATUS_OK;
4137 /*********************************************************************
4140 update an alias's comment.
4141 *********************************************************************/
4143 NTSTATUS _samr_set_aliasinfo(pipes_struct *p, SAMR_Q_SET_ALIASINFO *q_u, SAMR_R_SET_ALIASINFO *r_u)
4147 ALIAS_INFO_CTR *ctr;
4150 if (!get_lsa_policy_samr_sid(p, &q_u->alias_pol, &group_sid, &acc_granted))
4151 return NT_STATUS_INVALID_HANDLE;
4153 if (!NT_STATUS_IS_OK(r_u->status = access_check_samr_function(acc_granted, SA_RIGHT_ALIAS_SET_INFO, "_samr_set_aliasinfo"))) {
4157 if (!get_local_group_from_sid(group_sid, &map, MAPPING_WITH_PRIV))
4158 return NT_STATUS_NO_SUCH_GROUP;
4162 switch (ctr->switch_value1) {
4164 unistr2_to_ascii(map.comment, &(ctr->alias.info3.uni_acct_desc), sizeof(map.comment)-1);
4167 free_privilege(&map.priv_set);
4168 return NT_STATUS_INVALID_INFO_CLASS;
4171 if(!pdb_update_group_mapping_entry(&map)) {
4172 free_privilege(&map.priv_set);
4173 return NT_STATUS_NO_SUCH_GROUP;
4176 free_privilege(&map.priv_set);
4178 return NT_STATUS_OK;
4181 /*********************************************************************
4182 _samr_get_dom_pwinfo
4183 *********************************************************************/
4185 NTSTATUS _samr_get_dom_pwinfo(pipes_struct *p, SAMR_Q_GET_DOM_PWINFO *q_u, SAMR_R_GET_DOM_PWINFO *r_u)
4187 /* Perform access check. Since this rpc does not require a
4188 policy handle it will not be caught by the access checks on
4189 SAMR_CONNECT or SAMR_CONNECT_ANON. */
4191 if (!pipe_access_check(p)) {
4192 DEBUG(3, ("access denied to samr_get_dom_pwinfo\n"));
4193 r_u->status = NT_STATUS_ACCESS_DENIED;
4197 /* Actually, returning zeros here works quite well :-). */
4199 return NT_STATUS_OK;
4202 /*********************************************************************
4204 *********************************************************************/
4206 NTSTATUS _samr_open_group(pipes_struct *p, SAMR_Q_OPEN_GROUP *q_u, SAMR_R_OPEN_GROUP *r_u)
4211 struct samr_info *info;
4212 SEC_DESC *psd = NULL;
4219 if (!get_lsa_policy_samr_sid(p, &q_u->domain_pol, &sid, &acc_granted))
4220 return NT_STATUS_INVALID_HANDLE;
4222 if (!NT_STATUS_IS_OK(status = access_check_samr_function(acc_granted, SA_RIGHT_DOMAIN_OPEN_ACCOUNT, "_samr_open_group"))) {
4226 /*check if access can be granted as requested by client. */
4227 samr_make_grp_obj_sd(p->mem_ctx, &psd, &sd_size);
4228 se_map_generic(&des_access,&grp_generic_mapping);
4229 if (!NT_STATUS_IS_OK(status =
4230 access_check_samr_object(psd, p->pipe_user.nt_user_token,
4231 des_access, &acc_granted, "_samr_open_group"))) {
4236 /* this should not be hard-coded like this */
4237 if (!sid_equal(&sid, get_global_sam_sid()))
4238 return NT_STATUS_ACCESS_DENIED;
4240 sid_copy(&info_sid, get_global_sam_sid());
4241 sid_append_rid(&info_sid, q_u->rid_group);
4242 sid_to_string(sid_string, &info_sid);
4244 if ((info = get_samr_info_by_sid(&info_sid)) == NULL)
4245 return NT_STATUS_NO_MEMORY;
4247 info->acc_granted = acc_granted;
4249 DEBUG(10, ("_samr_open_group:Opening SID: %s\n", sid_string));
4251 /* check if that group really exists */
4252 if (!get_domain_group_from_sid(info->sid, &map, MAPPING_WITHOUT_PRIV))
4253 return NT_STATUS_NO_SUCH_GROUP;
4255 /* get a (unique) handle. open a policy on it. */
4256 if (!create_policy_hnd(p, &r_u->pol, free_samr_info, (void *)info))
4257 return NT_STATUS_OBJECT_NAME_NOT_FOUND;
4259 return NT_STATUS_OK;
4262 /*********************************************************************
4264 *********************************************************************/
4266 NTSTATUS _samr_unknown_2d(pipes_struct *p, SAMR_Q_UNKNOWN_2D *q_u, SAMR_R_UNKNOWN_2D *r_u)
4268 DEBUG(0,("_samr_unknown_2d: Not yet implemented.\n"));
4269 return NT_STATUS_NOT_IMPLEMENTED;
4272 /*******************************************************************
4274 ********************************************************************/
4276 NTSTATUS _samr_unknown_2e(pipes_struct *p, SAMR_Q_UNKNOWN_2E *q_u, SAMR_R_UNKNOWN_2E *r_u)
4278 struct samr_info *info = NULL;
4280 uint32 min_pass_len,pass_hist,flag;
4281 time_t u_expire, u_min_age;
4282 NTTIME nt_expire, nt_min_age;
4284 time_t u_lock_duration, u_reset_time;
4285 NTTIME nt_lock_duration, nt_reset_time;
4291 uint32 num_users=0, num_groups=0, num_aliases=0;
4293 uint32 account_policy_temp;
4295 if ((ctr = (SAM_UNK_CTR *)talloc_zero(p->mem_ctx, sizeof(SAM_UNK_CTR))) == NULL)
4296 return NT_STATUS_NO_MEMORY;
4300 r_u->status = NT_STATUS_OK;
4302 DEBUG(5,("_samr_unknown_2e: %d\n", __LINE__));
4304 /* find the policy handle. open a policy on it. */
4305 if (!find_policy_by_hnd(p, &q_u->domain_pol, (void **)&info))
4306 return NT_STATUS_INVALID_HANDLE;
4308 switch (q_u->switch_value) {
4310 account_policy_get(AP_MIN_PASSWORD_LEN, &account_policy_temp);
4311 min_pass_len = account_policy_temp;
4313 account_policy_get(AP_PASSWORD_HISTORY, &account_policy_temp);
4314 pass_hist = account_policy_temp;
4316 account_policy_get(AP_USER_MUST_LOGON_TO_CHG_PASS, &account_policy_temp);
4317 flag = account_policy_temp;
4319 account_policy_get(AP_MAX_PASSWORD_AGE, &account_policy_temp);
4320 u_expire = account_policy_temp;
4322 account_policy_get(AP_MIN_PASSWORD_AGE, &account_policy_temp);
4323 u_min_age = account_policy_temp;
4325 unix_to_nt_time_abs(&nt_expire, u_expire);
4326 unix_to_nt_time_abs(&nt_min_age, u_min_age);
4328 init_unk_info1(&ctr->info.inf1, (uint16)min_pass_len, (uint16)pass_hist,
4329 flag, nt_expire, nt_min_age);
4333 r_u->status=load_sampwd_entries(info, ACB_NORMAL, False);
4335 if (!NT_STATUS_IS_OK(r_u->status)) {
4336 DEBUG(5, ("_samr_unknown_2e: load_sampwd_entries failed\n"));
4339 num_users=info->disp_info.num_user_account;
4342 r_u->status=load_group_domain_entries(info, get_global_sam_sid());
4343 if (NT_STATUS_IS_ERR(r_u->status)) {
4344 DEBUG(5, ("_samr_unknown_2e: load_group_domain_entries failed\n"));
4347 num_groups=info->disp_info.num_group_account;
4350 /* The time call below is to get a sequence number for the sam. FIXME !!! JRA. */
4351 init_unk_info2(&ctr->info.inf2, lp_workgroup(), global_myname(), (uint32) time(NULL),
4352 num_users, num_groups, num_aliases);
4355 account_policy_get(AP_TIME_TO_LOGOUT, &account_policy_temp);
4356 u_logout = account_policy_temp;
4358 unix_to_nt_time_abs(&nt_logout, u_logout);
4360 init_unk_info3(&ctr->info.inf3, nt_logout);
4363 init_unk_info5(&ctr->info.inf5, global_myname());
4366 init_unk_info6(&ctr->info.inf6);
4369 init_unk_info7(&ctr->info.inf7);
4372 account_policy_get(AP_LOCK_ACCOUNT_DURATION, &account_policy_temp);
4373 u_lock_duration = account_policy_temp;
4375 account_policy_get(AP_RESET_COUNT_TIME, &account_policy_temp);
4376 u_reset_time = account_policy_temp;
4378 account_policy_get(AP_BAD_ATTEMPT_LOCKOUT, &account_policy_temp);
4379 lockout = account_policy_temp;
4381 unix_to_nt_time_abs(&nt_lock_duration, u_lock_duration);
4382 unix_to_nt_time_abs(&nt_reset_time, u_reset_time);
4384 init_unk_info12(&ctr->info.inf12, nt_lock_duration, nt_reset_time, (uint16)lockout);
4387 return NT_STATUS_INVALID_INFO_CLASS;
4390 init_samr_r_samr_unknown_2e(r_u, q_u->switch_value, ctr, NT_STATUS_OK);
4392 DEBUG(5,("_samr_unknown_2e: %d\n", __LINE__));
4397 /*******************************************************************
4399 ********************************************************************/
4401 NTSTATUS _samr_set_dom_info(pipes_struct *p, SAMR_Q_SET_DOMAIN_INFO *q_u, SAMR_R_SET_DOMAIN_INFO *r_u)
4403 time_t u_expire, u_min_age;
4405 time_t u_lock_duration, u_reset_time;
4407 r_u->status = NT_STATUS_OK;
4409 DEBUG(5,("_samr_set_dom_info: %d\n", __LINE__));
4411 /* find the policy handle. open a policy on it. */
4412 if (!find_policy_by_hnd(p, &q_u->domain_pol, NULL))
4413 return NT_STATUS_INVALID_HANDLE;
4415 DEBUG(5,("_samr_set_dom_info: switch_value: %d\n", q_u->switch_value));
4417 switch (q_u->switch_value) {
4419 u_expire=nt_time_to_unix_abs(&q_u->ctr->info.inf1.expire);
4420 u_min_age=nt_time_to_unix_abs(&q_u->ctr->info.inf1.min_passwordage);
4422 account_policy_set(AP_MIN_PASSWORD_LEN, (uint32)q_u->ctr->info.inf1.min_length_password);
4423 account_policy_set(AP_PASSWORD_HISTORY, (uint32)q_u->ctr->info.inf1.password_history);
4424 account_policy_set(AP_USER_MUST_LOGON_TO_CHG_PASS, (uint32)q_u->ctr->info.inf1.flag);
4425 account_policy_set(AP_MAX_PASSWORD_AGE, (int)u_expire);
4426 account_policy_set(AP_MIN_PASSWORD_AGE, (int)u_min_age);
4431 u_logout=nt_time_to_unix_abs(&q_u->ctr->info.inf3.logout);
4432 account_policy_set(AP_TIME_TO_LOGOUT, (int)u_logout);
4441 u_lock_duration=nt_time_to_unix_abs(&q_u->ctr->info.inf12.duration);
4442 u_reset_time=nt_time_to_unix_abs(&q_u->ctr->info.inf12.reset_count);
4444 account_policy_set(AP_LOCK_ACCOUNT_DURATION, (int)u_lock_duration);
4445 account_policy_set(AP_RESET_COUNT_TIME, (int)u_reset_time);
4446 account_policy_set(AP_BAD_ATTEMPT_LOCKOUT, (uint32)q_u->ctr->info.inf12.bad_attempt_lockout);
4449 return NT_STATUS_INVALID_INFO_CLASS;
4452 init_samr_r_set_domain_info(r_u, NT_STATUS_OK);
4454 DEBUG(5,("_samr_set_dom_info: %d\n", __LINE__));