3 * Unix SMB/Netbios implementation.
5 * RPC Pipe client / server routines
6 * Copyright (C) Andrew Tridgell 1992-1997,
7 * Copyright (C) Luke Kenneth Casson Leighton 1996-1997,
8 * Copyright (C) Paul Ashton 1997.
10 * This program is free software; you can redistribute it and/or modify
11 * it under the terms of the GNU General Public License as published by
12 * the Free Software Foundation; either version 2 of the License, or
13 * (at your option) any later version.
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU General Public License for more details.
20 * You should have received a copy of the GNU General Public License
21 * along with this program; if not, write to the Free Software
22 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
29 extern int DEBUGLEVEL;
31 extern fstring global_sam_name;
32 extern pstring global_myname;
33 extern DOM_SID global_sam_sid;
34 extern DOM_SID global_sid_S_1_1;
35 extern DOM_SID global_sid_S_1_5_20;
37 /*******************************************************************
38 This next function should be replaced with something that
39 dynamically returns the correct user info..... JRA.
40 ********************************************************************/
42 static BOOL get_sampwd_entries(SAM_USER_INFO_21 *pw_buf,
44 int *total_entries, int *num_entries,
49 struct sam_passwd *pwd = NULL;
54 if (pw_buf == NULL) return False;
56 vp = startsmbpwent(False);
59 DEBUG(0, ("get_sampwd_entries: Unable to open SMB password database.\n"));
63 while (((pwd = getsam21pwent(vp)) != NULL) && (*num_entries) < max_num_entries)
69 /* skip the requested number of entries.
70 not very efficient, but hey...
72 if (acb_mask == 0 || IS_BITS_SET_SOME(pwd->acct_ctrl, acb_mask))
79 user_name_len = strlen(pwd->nt_name);
80 make_unistr2(&(pw_buf[(*num_entries)].uni_user_name), pwd->nt_name, user_name_len);
81 make_uni_hdr(&(pw_buf[(*num_entries)].hdr_user_name), user_name_len);
82 pw_buf[(*num_entries)].user_rid = pwd->user_rid;
83 bzero( pw_buf[(*num_entries)].nt_pwd , 16);
85 /* Now check if the NT compatible password is available. */
86 if (pwd->smb_nt_passwd != NULL)
88 memcpy( pw_buf[(*num_entries)].nt_pwd , pwd->smb_nt_passwd, 16);
91 pw_buf[(*num_entries)].acb_info = (uint16)pwd->acct_ctrl;
93 DEBUG(5, ("entry idx: %d user %s, rid 0x%x, acb %x",
94 (*num_entries), pwd->nt_name,
95 pwd->user_rid, pwd->acct_ctrl));
97 if (acb_mask == 0 || IS_BITS_SET_SOME(pwd->acct_ctrl, acb_mask))
99 DEBUG(5,(" acb_mask %x accepts\n", acb_mask));
104 DEBUG(5,(" acb_mask %x rejects\n", acb_mask));
112 return (*num_entries) > 0;
115 /*******************************************************************
117 ********************************************************************/
118 static void samr_reply_close_hnd(SAMR_Q_CLOSE_HND *q_u,
121 SAMR_R_CLOSE_HND r_u;
123 /* set up the SAMR unknown_1 response */
124 bzero(r_u.pol.data, POL_HND_SIZE);
126 /* close the policy handle */
127 if (close_lsa_policy_hnd(&(q_u->pol)))
133 r_u.status = 0xC0000000 | NT_STATUS_OBJECT_NAME_INVALID;
136 DEBUG(5,("samr_reply_close_hnd: %d\n", __LINE__));
138 /* store the response in the SMB stream */
139 samr_io_r_close_hnd("", &r_u, rdata, 0);
141 DEBUG(5,("samr_reply_close_hnd: %d\n", __LINE__));
145 /*******************************************************************
147 ********************************************************************/
148 static void api_samr_close_hnd( pipes_struct *p, prs_struct *data, prs_struct *rdata)
150 SAMR_Q_CLOSE_HND q_u;
151 samr_io_q_close_hnd("", &q_u, data, 0);
152 samr_reply_close_hnd(&q_u, rdata);
156 /*******************************************************************
157 samr_reply_open_domain
158 ********************************************************************/
159 static void samr_reply_open_domain(SAMR_Q_OPEN_DOMAIN *q_u,
162 SAMR_R_OPEN_DOMAIN r_u;
163 BOOL pol_open = False;
167 /* find the connection policy handle. */
168 if (r_u.status == 0x0 && (find_lsa_policy_by_hnd(&(q_u->connect_pol)) == -1))
170 r_u.status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
173 /* get a (unique) handle. open a policy on it. */
174 if (r_u.status == 0x0 && !(pol_open = open_lsa_policy_hnd(&(r_u.domain_pol))))
176 r_u.status = 0xC0000000 | NT_STATUS_OBJECT_NAME_NOT_FOUND;
179 /* associate the domain SID with the (unique) handle. */
180 if (r_u.status == 0x0 && !set_lsa_policy_samr_sid(&(r_u.domain_pol), &(q_u->dom_sid.sid)))
182 /* oh, whoops. don't know what error message to return, here */
183 r_u.status = 0xC0000000 | NT_STATUS_OBJECT_NAME_NOT_FOUND;
186 if (r_u.status != 0 && pol_open)
188 close_lsa_policy_hnd(&(r_u.domain_pol));
191 DEBUG(5,("samr_open_domain: %d\n", __LINE__));
193 /* store the response in the SMB stream */
194 samr_io_r_open_domain("", &r_u, rdata, 0);
196 DEBUG(5,("samr_open_domain: %d\n", __LINE__));
200 /*******************************************************************
202 ********************************************************************/
203 static void api_samr_open_domain( pipes_struct *p, prs_struct *data, prs_struct *rdata)
205 SAMR_Q_OPEN_DOMAIN q_u;
206 samr_io_q_open_domain("", &q_u, data, 0);
207 samr_reply_open_domain(&q_u, rdata);
211 /*******************************************************************
212 samr_reply_unknown_2c
213 ********************************************************************/
214 static void samr_reply_unknown_2c(SAMR_Q_UNKNOWN_2C *q_u,
217 SAMR_R_UNKNOWN_2C r_u;
220 /* find the policy handle. open a policy on it. */
221 if (status == 0x0 && (find_lsa_policy_by_hnd(&(q_u->user_pol)) == -1))
223 status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
226 /* find the user's rid */
227 if ((status == 0x0) && (get_lsa_policy_samr_rid(&(q_u->user_pol)) == 0xffffffff))
229 status = 0xC0000000 | NT_STATUS_OBJECT_TYPE_MISMATCH;
232 make_samr_r_unknown_2c(&r_u, status);
234 DEBUG(5,("samr_unknown_2c: %d\n", __LINE__));
236 /* store the response in the SMB stream */
237 samr_io_r_unknown_2c("", &r_u, rdata, 0);
239 DEBUG(5,("samr_unknown_2c: %d\n", __LINE__));
243 /*******************************************************************
245 ********************************************************************/
246 static void api_samr_unknown_2c( pipes_struct *p, prs_struct *data, prs_struct *rdata)
248 SAMR_Q_UNKNOWN_2C q_u;
249 samr_io_q_unknown_2c("", &q_u, data, 0);
250 samr_reply_unknown_2c(&q_u, rdata);
254 /*******************************************************************
256 ********************************************************************/
257 static void samr_reply_unknown_3(SAMR_Q_UNKNOWN_3 *q_u,
260 SAMR_R_UNKNOWN_3 r_u;
261 DOM_SID3 sid[MAX_SAM_SIDS];
267 /* find the policy handle. open a policy on it. */
268 if (status == 0x0 && (find_lsa_policy_by_hnd(&(q_u->user_pol)) == -1))
270 status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
273 /* find the user's rid */
274 if (status == 0x0 && (rid = get_lsa_policy_samr_rid(&(q_u->user_pol))) == 0xffffffff)
276 status = 0xC0000000 | NT_STATUS_OBJECT_TYPE_MISMATCH;
283 usr_sid = global_sam_sid;
285 SMB_ASSERT_ARRAY(usr_sid.sub_auths, usr_sid.num_auths+1);
290 sid_append_rid(&usr_sid, rid);
292 /* maybe need another 1 or 2 (S-1-5-0x20-0x220 and S-1-5-20-0x224) */
293 /* these two are DOMAIN_ADMIN and DOMAIN_ACCT_OP group RIDs */
294 make_dom_sid3(&(sid[0]), 0x035b, 0x0002, &global_sid_S_1_1);
295 make_dom_sid3(&(sid[1]), 0x0044, 0x0002, &usr_sid);
298 make_samr_r_unknown_3(&r_u,
300 0x00000014, 0x0002, 0x0070,
303 DEBUG(5,("samr_unknown_3: %d\n", __LINE__));
305 /* store the response in the SMB stream */
306 samr_io_r_unknown_3("", &r_u, rdata, 0);
308 DEBUG(5,("samr_unknown_3: %d\n", __LINE__));
312 /*******************************************************************
314 ********************************************************************/
315 static void api_samr_unknown_3( pipes_struct *p, prs_struct *data, prs_struct *rdata)
317 SAMR_Q_UNKNOWN_3 q_u;
318 samr_io_q_unknown_3("", &q_u, data, 0);
319 samr_reply_unknown_3(&q_u, rdata);
323 /*******************************************************************
324 samr_reply_enum_dom_users
325 ********************************************************************/
326 static void samr_reply_enum_dom_users(SAMR_Q_ENUM_DOM_USERS *q_u,
329 SAMR_R_ENUM_DOM_USERS r_e;
330 SAM_USER_INFO_21 pass[MAX_SAM_ENTRIES];
336 /* find the policy handle. open a policy on it. */
337 if (r_e.status == 0x0 && (find_lsa_policy_by_hnd(&(q_u->pol)) == -1))
339 r_e.status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
342 DEBUG(5,("samr_reply_enum_dom_users: %d\n", __LINE__));
345 get_sampwd_entries(pass, q_u->start_idx, &total_entries, &num_entries,
346 MAX_SAM_ENTRIES, q_u->acb_mask);
349 make_samr_r_enum_dom_users(&r_e,
350 q_u->start_idx + num_entries, num_entries,
353 /* store the response in the SMB stream */
354 samr_io_r_enum_dom_users("", &r_e, rdata, 0);
361 if (r_e.uni_acct_name != NULL)
363 free(r_e.uni_acct_name);
366 DEBUG(5,("samr_enum_dom_users: %d\n", __LINE__));
370 /*******************************************************************
371 api_samr_enum_dom_users
372 ********************************************************************/
373 static void api_samr_enum_dom_users( pipes_struct *p, prs_struct *data, prs_struct *rdata)
375 SAMR_Q_ENUM_DOM_USERS q_e;
376 samr_io_q_enum_dom_users("", &q_e, data, 0);
377 samr_reply_enum_dom_users(&q_e, rdata);
381 /*******************************************************************
382 samr_reply_add_groupmem
383 ********************************************************************/
384 static void samr_reply_add_groupmem(SAMR_Q_ADD_GROUPMEM *q_u,
387 SAMR_R_ADD_GROUPMEM r_e;
390 fstring group_sid_str;
394 /* find the policy handle. open a policy on it. */
395 if (r_e.status == 0x0 && !get_lsa_policy_samr_sid(&q_u->pol, &group_sid))
397 r_e.status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
401 sid_to_string(group_sid_str, &group_sid);
402 sid_split_rid(&group_sid, &group_rid);
405 if (r_e.status == 0x0)
407 DEBUG(10,("sid is %s\n", group_sid_str));
409 if (sid_equal(&group_sid, &global_sam_sid))
411 DEBUG(10,("lookup on Domain SID\n"));
414 r_e.status = add_group_member(group_rid, q_u->rid) ? 0x0 : (0xC0000000 | NT_STATUS_ACCESS_DENIED);
419 r_e.status = 0xC0000000 | NT_STATUS_NO_SUCH_GROUP;
423 /* store the response in the SMB stream */
424 samr_io_r_add_groupmem("", &r_e, rdata, 0);
426 DEBUG(5,("samr_add_groupmem: %d\n", __LINE__));
429 /*******************************************************************
430 api_samr_add_groupmem
431 ********************************************************************/
432 static void api_samr_add_groupmem( pipes_struct *p, prs_struct *data, prs_struct *rdata)
434 SAMR_Q_ADD_GROUPMEM q_e;
435 samr_io_q_add_groupmem("", &q_e, data, 0);
436 samr_reply_add_groupmem(&q_e, rdata);
439 /*******************************************************************
440 samr_reply_del_groupmem
441 ********************************************************************/
442 static void samr_reply_del_groupmem(SAMR_Q_DEL_GROUPMEM *q_u,
445 SAMR_R_DEL_GROUPMEM r_e;
448 fstring group_sid_str;
452 /* find the policy handle. open a policy on it. */
453 if (r_e.status == 0x0 && !get_lsa_policy_samr_sid(&q_u->pol, &group_sid))
455 r_e.status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
459 sid_to_string(group_sid_str, &group_sid);
460 sid_split_rid(&group_sid, &group_rid);
463 if (r_e.status == 0x0)
465 DEBUG(10,("sid is %s\n", group_sid_str));
467 if (sid_equal(&group_sid, &global_sam_sid))
469 DEBUG(10,("lookup on Domain SID\n"));
472 r_e.status = del_group_member(group_rid, q_u->rid) ? 0x0 : (0xC0000000 | NT_STATUS_ACCESS_DENIED);
477 r_e.status = 0xC0000000 | NT_STATUS_NO_SUCH_GROUP;
481 /* store the response in the SMB stream */
482 samr_io_r_del_groupmem("", &r_e, rdata, 0);
484 DEBUG(5,("samr_del_groupmem: %d\n", __LINE__));
487 /*******************************************************************
488 api_samr_del_groupmem
489 ********************************************************************/
490 static void api_samr_del_groupmem( pipes_struct *p, prs_struct *data, prs_struct *rdata)
492 SAMR_Q_DEL_GROUPMEM q_e;
493 samr_io_q_del_groupmem("", &q_e, data, 0);
494 samr_reply_del_groupmem(&q_e, rdata);
497 /*******************************************************************
498 samr_reply_add_aliasmem
499 ********************************************************************/
500 static void samr_reply_add_aliasmem(SAMR_Q_ADD_ALIASMEM *q_u,
503 SAMR_R_ADD_ALIASMEM r_e;
506 fstring alias_sid_str;
510 /* find the policy handle. open a policy on it. */
511 if (r_e.status == 0x0 && !get_lsa_policy_samr_sid(&q_u->alias_pol, &alias_sid))
513 r_e.status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
517 sid_to_string(alias_sid_str, &alias_sid);
518 sid_split_rid(&alias_sid, &alias_rid);
521 if (r_e.status == 0x0)
523 DEBUG(10,("sid is %s\n", alias_sid_str));
525 if (sid_equal(&alias_sid, &global_sam_sid))
527 DEBUG(10,("add member on Domain SID\n"));
530 r_e.status = add_alias_member(alias_rid, &q_u->sid.sid) ? 0x0 : (0xC0000000 | NT_STATUS_ACCESS_DENIED);
533 else if (sid_equal(&alias_sid, &global_sid_S_1_5_20))
535 DEBUG(10,("add member on BUILTIN SID\n"));
538 r_e.status = add_builtin_member(alias_rid, &q_u->sid.sid) ? 0x0 : (0xC0000000 | NT_STATUS_ACCESS_DENIED);
543 r_e.status = 0xC0000000 | NT_STATUS_NO_SUCH_ALIAS;
547 /* store the response in the SMB stream */
548 samr_io_r_add_aliasmem("", &r_e, rdata, 0);
550 DEBUG(5,("samr_add_aliasmem: %d\n", __LINE__));
553 /*******************************************************************
554 api_samr_add_aliasmem
555 ********************************************************************/
556 static void api_samr_add_aliasmem( pipes_struct *p, prs_struct *data, prs_struct *rdata)
558 SAMR_Q_ADD_ALIASMEM q_e;
559 samr_io_q_add_aliasmem("", &q_e, data, 0);
560 samr_reply_add_aliasmem(&q_e, rdata);
563 /*******************************************************************
564 samr_reply_del_aliasmem
565 ********************************************************************/
566 static void samr_reply_del_aliasmem(SAMR_Q_DEL_ALIASMEM *q_u,
569 SAMR_R_DEL_ALIASMEM r_e;
572 fstring alias_sid_str;
576 /* find the policy handle. open a policy on it. */
577 if (r_e.status == 0x0 && !get_lsa_policy_samr_sid(&q_u->alias_pol, &alias_sid))
579 r_e.status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
583 sid_to_string(alias_sid_str, &alias_sid);
584 sid_split_rid(&alias_sid, &alias_rid);
587 if (r_e.status == 0x0)
589 DEBUG(10,("sid is %s\n", alias_sid_str));
591 if (sid_equal(&alias_sid, &global_sam_sid))
593 DEBUG(10,("del member on Domain SID\n"));
596 r_e.status = del_alias_member(alias_rid, &q_u->sid.sid) ? 0x0 : (0xC0000000 | NT_STATUS_ACCESS_DENIED);
599 else if (sid_equal(&alias_sid, &global_sid_S_1_5_20))
601 DEBUG(10,("del member on BUILTIN SID\n"));
604 r_e.status = del_builtin_member(alias_rid, &q_u->sid.sid) ? 0x0 : (0xC0000000 | NT_STATUS_ACCESS_DENIED);
609 r_e.status = 0xC0000000 | NT_STATUS_NO_SUCH_ALIAS;
613 /* store the response in the SMB stream */
614 samr_io_r_del_aliasmem("", &r_e, rdata, 0);
616 DEBUG(5,("samr_del_aliasmem: %d\n", __LINE__));
619 /*******************************************************************
620 api_samr_del_aliasmem
621 ********************************************************************/
622 static void api_samr_del_aliasmem( pipes_struct *p, prs_struct *data, prs_struct *rdata)
624 SAMR_Q_DEL_ALIASMEM q_e;
625 samr_io_q_del_aliasmem("", &q_e, data, 0);
626 samr_reply_del_aliasmem(&q_e, rdata);
629 /*******************************************************************
630 samr_reply_enum_domains
631 ********************************************************************/
632 static void samr_reply_enum_domains(SAMR_Q_ENUM_DOMAINS *q_u,
635 SAMR_R_ENUM_DOMAINS r_e;
637 uint32 num_entries = 0;
640 r_e.num_entries2 = 0;
646 /* find the connection policy handle. */
647 if (r_e.status == 0x0 && (find_lsa_policy_by_hnd(&(q_u->pol)) == -1))
649 r_e.status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
652 DEBUG(5,("samr_reply_enum_domains:\n"));
654 if (!enumdomains(&doms, &num_entries))
656 r_e.status = 0xC0000000 | NT_STATUS_NO_MEMORY;
659 if (r_e.status == 0x0)
661 make_samr_r_enum_domains(&r_e,
662 q_u->start_idx + num_entries,
663 num_entries, doms, r_e.status);
666 /* store the response in the SMB stream */
667 samr_io_r_enum_domains("", &r_e, rdata, 0);
669 free_char_array(num_entries, doms);
676 if (r_e.uni_dom_name != NULL)
678 free(r_e.uni_dom_name);
681 DEBUG(5,("samr_enum_domains: %d\n", __LINE__));
684 /*******************************************************************
685 api_samr_enum_domains
686 ********************************************************************/
687 static void api_samr_enum_domains( pipes_struct *p, prs_struct *data, prs_struct *rdata)
689 SAMR_Q_ENUM_DOMAINS q_e;
691 /* grab the samr open */
692 samr_io_q_enum_domains("", &q_e, data, 0);
694 /* construct reply. */
695 samr_reply_enum_domains(&q_e, rdata);
698 /*******************************************************************
699 samr_reply_enum_dom_groups
700 ********************************************************************/
701 static void samr_reply_enum_dom_groups(SAMR_Q_ENUM_DOM_GROUPS *q_u,
704 SAMR_R_ENUM_DOM_GROUPS r_e;
705 DOMAIN_GRP *grps = NULL;
711 r_e.num_entries2 = 0;
713 /* find the policy handle. open a policy on it. */
714 if (r_e.status == 0x0 && !get_lsa_policy_samr_sid(&q_u->pol, &sid))
716 r_e.status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
719 sid_to_string(sid_str, &sid);
721 DEBUG(5,("samr_reply_enum_dom_groups: sid %s\n", sid_str));
723 if (sid_equal(&sid, &global_sam_sid))
728 ret = enumdomgroups(&grps, &num_entries);
732 r_e.status = 0xC0000000 | NT_STATUS_NO_MEMORY;
736 if (r_e.status == 0x0)
738 make_samr_r_enum_dom_groups(&r_e,
739 q_u->start_idx + num_entries,
740 num_entries, grps, r_e.status);
743 /* store the response in the SMB stream */
744 samr_io_r_enum_dom_groups("", &r_e, rdata, 0);
756 if (r_e.uni_grp_name != NULL)
758 free(r_e.uni_grp_name);
761 DEBUG(5,("samr_enum_dom_groups: %d\n", __LINE__));
764 /*******************************************************************
765 api_samr_enum_dom_groups
766 ********************************************************************/
767 static void api_samr_enum_dom_groups( pipes_struct *p, prs_struct *data, prs_struct *rdata)
769 SAMR_Q_ENUM_DOM_GROUPS q_e;
771 /* grab the samr open */
772 samr_io_q_enum_dom_groups("", &q_e, data, 0);
774 /* construct reply. */
775 samr_reply_enum_dom_groups(&q_e, rdata);
779 /*******************************************************************
780 samr_reply_enum_dom_aliases
781 ********************************************************************/
782 static void samr_reply_enum_dom_aliases(SAMR_Q_ENUM_DOM_ALIASES *q_u,
785 SAMR_R_ENUM_DOM_ALIASES r_e;
786 LOCAL_GRP *alss = NULL;
792 r_e.num_entries2 = 0;
794 /* find the policy handle. open a policy on it. */
795 if (r_e.status == 0x0 && !get_lsa_policy_samr_sid(&q_u->pol, &sid))
797 r_e.status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
800 sid_to_string(sid_str, &sid);
802 DEBUG(5,("samr_reply_enum_dom_aliases: sid %s\n", sid_str));
804 /* well-known aliases */
805 if (sid_equal(&sid, &global_sid_S_1_5_20))
808 /* builtin aliases */
811 ret = enumdombuiltins(&alss, &num_entries);
815 r_e.status = 0xC0000000 | NT_STATUS_NO_MEMORY;
818 else if (sid_equal(&sid, &global_sam_sid))
824 ret = enumdomaliases(&alss, &num_entries);
828 r_e.status = 0xC0000000 | NT_STATUS_NO_MEMORY;
832 if (r_e.status == 0x0)
834 make_samr_r_enum_dom_aliases(&r_e,
835 q_u->start_idx + num_entries,
836 num_entries, alss, r_e.status);
839 /* store the response in the SMB stream */
840 samr_io_r_enum_dom_aliases("", &r_e, rdata, 0);
852 if (r_e.uni_grp_name != NULL)
854 free(r_e.uni_grp_name);
857 DEBUG(5,("samr_enum_dom_aliases: %d\n", __LINE__));
861 /*******************************************************************
862 api_samr_enum_dom_aliases
863 ********************************************************************/
864 static void api_samr_enum_dom_aliases( pipes_struct *p, prs_struct *data, prs_struct *rdata)
866 SAMR_Q_ENUM_DOM_ALIASES q_e;
868 /* grab the samr open */
869 samr_io_q_enum_dom_aliases("", &q_e, data, 0);
871 /* construct reply. */
872 samr_reply_enum_dom_aliases(&q_e, rdata);
876 /*******************************************************************
877 samr_reply_query_dispinfo
878 ********************************************************************/
879 static void samr_reply_query_dispinfo(SAMR_Q_QUERY_DISPINFO *q_u,
882 SAMR_R_QUERY_DISPINFO r_e;
883 SAM_DISPINFO_CTR ctr;
884 SAM_USER_INFO_21 pass[MAX_SAM_ENTRIES];
885 DOMAIN_GRP *grps = NULL;
886 DOMAIN_GRP *sam_grps = NULL;
887 uint32 data_size = 0;
889 uint16 acb_mask = ACB_NORMAL;
890 int num_sam_entries = 0;
894 DEBUG(5,("samr_reply_query_dispinfo: %d\n", __LINE__));
896 /* find the policy handle. open a policy on it. */
897 if (find_lsa_policy_by_hnd(&(q_u->domain_pol)) == -1)
899 status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
900 DEBUG(5,("samr_reply_query_dispinfo: invalid handle\n"));
907 /* Get what we need from the password database */
908 switch (q_u->switch_level)
912 acb_mask = ACB_WSTRUST;
918 get_sampwd_entries(pass, q_u->start_idx,
919 &total_entries, &num_sam_entries,
920 MAX_SAM_ENTRIES, acb_mask);
926 enumdomgroups(&sam_grps, &num_sam_entries);
928 if (q_u->start_idx < num_sam_entries) {
929 grps = sam_grps + q_u->start_idx;
930 num_sam_entries -= q_u->start_idx;
940 num_entries = num_sam_entries;
942 if (num_entries > q_u->max_entries)
944 num_entries = q_u->max_entries;
947 if (num_entries > MAX_SAM_ENTRIES)
949 num_entries = MAX_SAM_ENTRIES;
950 DEBUG(5,("limiting number of entries to %d\n",
954 data_size = q_u->max_size;
956 /* Now create reply structure */
957 switch (q_u->switch_level)
961 ctr.sam.info1 = malloc(sizeof(SAM_DISPINFO_1));
962 make_sam_dispinfo_1(ctr.sam.info1,
963 &num_entries, &data_size,
964 q_u->start_idx, pass);
969 ctr.sam.info2 = malloc(sizeof(SAM_DISPINFO_2));
970 make_sam_dispinfo_2(ctr.sam.info2,
971 &num_entries, &data_size,
972 q_u->start_idx, pass);
977 ctr.sam.info3 = malloc(sizeof(SAM_DISPINFO_3));
978 make_sam_dispinfo_3(ctr.sam.info3,
979 &num_entries, &data_size,
980 q_u->start_idx, grps);
985 ctr.sam.info4 = malloc(sizeof(SAM_DISPINFO_4));
986 make_sam_dispinfo_4(ctr.sam.info4,
987 &num_entries, &data_size,
988 q_u->start_idx, pass);
993 ctr.sam.info5 = malloc(sizeof(SAM_DISPINFO_5));
994 make_sam_dispinfo_5(ctr.sam.info5,
995 &num_entries, &data_size,
996 q_u->start_idx, grps);
1001 ctr.sam.info = NULL;
1002 status = 0xC0000000 | NT_STATUS_INVALID_INFO_CLASS;
1008 if ((status == 0) && (num_entries < num_sam_entries))
1010 status = STATUS_MORE_ENTRIES;
1013 make_samr_r_query_dispinfo(&r_e, num_entries, data_size,
1014 q_u->switch_level, &ctr, status);
1016 /* store the response in the SMB stream */
1017 samr_io_r_query_dispinfo("", &r_e, rdata, 0);
1019 /* free malloc'd areas */
1020 if (sam_grps != NULL)
1025 if (ctr.sam.info != NULL)
1030 DEBUG(5,("samr_reply_query_dispinfo: %d\n", __LINE__));
1033 /*******************************************************************
1034 api_samr_query_dispinfo
1035 ********************************************************************/
1036 static void api_samr_query_dispinfo( pipes_struct *p, prs_struct *data, prs_struct *rdata)
1038 SAMR_Q_QUERY_DISPINFO q_e;
1040 samr_io_q_query_dispinfo("", &q_e, data, 0);
1041 samr_reply_query_dispinfo(&q_e, rdata);
1044 /*******************************************************************
1045 samr_reply_delete_dom_group
1046 ********************************************************************/
1047 static void samr_reply_delete_dom_group(SAMR_Q_DELETE_DOM_GROUP *q_u,
1054 fstring group_sid_str;
1056 SAMR_R_DELETE_DOM_GROUP r_u;
1058 DEBUG(5,("samr_delete_dom_group: %d\n", __LINE__));
1060 /* find the policy handle. open a policy on it. */
1061 if (status == 0x0 && !get_lsa_policy_samr_sid(&q_u->group_pol, &group_sid))
1063 status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
1067 sid_to_string(group_sid_str, &group_sid );
1068 sid_split_rid(&group_sid, &group_rid);
1073 DEBUG(10,("sid is %s\n", group_sid_str));
1075 if (sid_equal(&group_sid, &global_sam_sid))
1077 DEBUG(10,("lookup on Domain SID\n"));
1080 status = del_group_entry(group_rid) ? 0x0 : (0xC0000000 | NT_STATUS_NO_SUCH_GROUP);
1081 unbecome_root(True);
1085 status = 0xC0000000 | NT_STATUS_NO_SUCH_GROUP;
1089 make_samr_r_delete_dom_group(&r_u, status);
1091 /* store the response in the SMB stream */
1092 samr_io_r_delete_dom_group("", &r_u, rdata, 0);
1095 /*******************************************************************
1096 api_samr_delete_dom_group
1097 ********************************************************************/
1098 static void api_samr_delete_dom_group( pipes_struct *p, prs_struct *data, prs_struct *rdata)
1100 SAMR_Q_DELETE_DOM_GROUP q_u;
1101 samr_io_q_delete_dom_group("", &q_u, data, 0);
1102 samr_reply_delete_dom_group(&q_u, rdata);
1106 /*******************************************************************
1107 samr_reply_query_groupmem
1108 ********************************************************************/
1109 static void samr_reply_query_groupmem(SAMR_Q_QUERY_GROUPMEM *q_u,
1114 DOMAIN_GRP_MEMBER *mem_grp = NULL;
1116 uint32 *attr = NULL;
1120 fstring group_sid_str;
1122 SAMR_R_QUERY_GROUPMEM r_u;
1124 DEBUG(5,("samr_query_groupmem: %d\n", __LINE__));
1126 /* find the policy handle. open a policy on it. */
1127 if (status == 0x0 && !get_lsa_policy_samr_sid(&q_u->group_pol, &group_sid))
1129 status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
1133 sid_to_string(group_sid_str, &group_sid );
1134 sid_split_rid(&group_sid, &group_rid);
1139 DEBUG(10,("sid is %s\n", group_sid_str));
1141 if (sid_equal(&group_sid, &global_sam_sid))
1143 DEBUG(10,("lookup on Domain SID\n"));
1146 status = getgrouprid(group_rid, &mem_grp, &num_rids) != NULL ? 0x0 : (0xC0000000 | NT_STATUS_NO_SUCH_GROUP);
1147 unbecome_root(True);
1151 status = 0xC0000000 | NT_STATUS_NO_SUCH_GROUP;
1155 if (status == 0x0 && num_rids > 0)
1157 rid = malloc(num_rids * sizeof(uint32));
1158 attr = malloc(num_rids * sizeof(uint32));
1159 if (mem_grp != NULL && rid != NULL && attr != NULL)
1162 for (i = 0; i < num_rids; i++)
1164 rid [i] = mem_grp[i].rid;
1165 attr[i] = mem_grp[i].attr;
1171 make_samr_r_query_groupmem(&r_u, num_rids, rid, attr, status);
1173 /* store the response in the SMB stream */
1174 samr_io_r_query_groupmem("", &r_u, rdata, 0);
1186 DEBUG(5,("samr_query_groupmem: %d\n", __LINE__));
1190 /*******************************************************************
1191 api_samr_query_groupmem
1192 ********************************************************************/
1193 static void api_samr_query_groupmem( pipes_struct *p, prs_struct *data, prs_struct *rdata)
1195 SAMR_Q_QUERY_GROUPMEM q_u;
1196 samr_io_q_query_groupmem("", &q_u, data, 0);
1197 samr_reply_query_groupmem(&q_u, rdata);
1201 /*******************************************************************
1202 samr_reply_query_groupinfo
1203 ********************************************************************/
1204 static void samr_reply_query_groupinfo(SAMR_Q_QUERY_GROUPINFO *q_u,
1207 SAMR_R_QUERY_GROUPINFO r_e;
1209 uint32 status = 0x0;
1213 /* find the policy handle. open a policy on it. */
1214 if (r_e.status == 0x0 && (find_lsa_policy_by_hnd(&(q_u->pol)) == -1))
1216 r_e.status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
1219 DEBUG(5,("samr_reply_query_groupinfo: %d\n", __LINE__));
1223 if (q_u->switch_level == 1)
1226 ctr.switch_value1 = 1;
1227 make_samr_group_info1(&ctr.group.info1,
1228 "fake account name",
1229 "fake account description", 2);
1231 else if (q_u->switch_level == 4)
1234 ctr.switch_value1 = 4;
1235 make_samr_group_info4(&ctr.group.info4,
1236 "fake account description");
1240 status = 0xC0000000 | NT_STATUS_INVALID_INFO_CLASS;
1244 make_samr_r_query_groupinfo(&r_e, status == 0 ? &ctr : NULL, status);
1246 /* store the response in the SMB stream */
1247 samr_io_r_query_groupinfo("", &r_e, rdata, 0);
1249 DEBUG(5,("samr_query_groupinfo: %d\n", __LINE__));
1253 /*******************************************************************
1254 api_samr_query_groupinfo
1255 ********************************************************************/
1256 static void api_samr_query_groupinfo( pipes_struct *p, prs_struct *data, prs_struct *rdata)
1258 SAMR_Q_QUERY_GROUPINFO q_e;
1259 samr_io_q_query_groupinfo("", &q_e, data, 0);
1260 samr_reply_query_groupinfo(&q_e, rdata);
1264 /*******************************************************************
1265 samr_reply_query_aliasinfo
1266 ********************************************************************/
1267 static void samr_reply_query_aliasinfo(SAMR_Q_QUERY_ALIASINFO *q_u,
1270 SAMR_R_QUERY_ALIASINFO r_e;
1272 uint32 status = 0x0;
1276 /* find the policy handle. open a policy on it. */
1277 if (r_e.status == 0x0 && (find_lsa_policy_by_hnd(&(q_u->pol)) == -1))
1279 r_e.status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
1282 DEBUG(5,("samr_reply_query_aliasinfo: %d\n", __LINE__));
1286 if (q_u->switch_level == 3)
1289 ctr.switch_value1 = 3;
1290 make_samr_alias_info3(&ctr.alias.info3, "<fake account description>");
1294 status = 0xC0000000 | NT_STATUS_INVALID_INFO_CLASS;
1298 make_samr_r_query_aliasinfo(&r_e, status == 0 ? &ctr : NULL, status);
1300 /* store the response in the SMB stream */
1301 samr_io_r_query_aliasinfo("", &r_e, rdata, 0);
1303 DEBUG(5,("samr_query_aliasinfo: %d\n", __LINE__));
1307 /*******************************************************************
1308 api_samr_query_aliasinfo
1309 ********************************************************************/
1310 static void api_samr_query_aliasinfo( pipes_struct *p, prs_struct *data, prs_struct *rdata)
1312 SAMR_Q_QUERY_ALIASINFO q_e;
1313 samr_io_q_query_aliasinfo("", &q_e, data, 0);
1314 samr_reply_query_aliasinfo(&q_e, rdata);
1318 /*******************************************************************
1319 samr_reply_query_useraliases
1320 ********************************************************************/
1321 static void samr_reply_query_useraliases(SAMR_Q_QUERY_USERALIASES *q_u,
1326 LOCAL_GRP *mem_grp = NULL;
1329 struct sam_passwd *sam_pass;
1333 fstring sam_sid_str;
1334 fstring dom_sid_str;
1335 fstring usr_sid_str;
1337 SAMR_R_QUERY_USERALIASES r_u;
1340 DEBUG(5,("samr_query_useraliases: %d\n", __LINE__));
1342 /* find the policy handle. open a policy on it. */
1343 if (status == 0x0 && !get_lsa_policy_samr_sid(&q_u->pol, &dom_sid))
1345 status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
1349 sid_to_string(dom_sid_str, &dom_sid );
1350 sid_to_string(sam_sid_str, &global_sam_sid);
1355 usr_sid = q_u->sid[0].sid;
1356 sid_split_rid(&usr_sid, &user_rid);
1357 sid_to_string(usr_sid_str, &usr_sid);
1363 /* find the user account */
1365 sam_pass = getsam21pwrid(user_rid);
1366 unbecome_root(True);
1368 if (sam_pass == NULL)
1370 status = 0xC0000000 | NT_STATUS_NO_SUCH_USER;
1377 DEBUG(10,("sid is %s\n", dom_sid_str));
1379 if (sid_equal(&dom_sid, &global_sid_S_1_5_20))
1381 DEBUG(10,("lookup on S-1-5-20\n"));
1384 getuserbuiltinntnam(sam_pass->nt_name, &mem_grp, &num_rids);
1385 unbecome_root(True);
1387 else if (sid_equal(&dom_sid, &usr_sid))
1389 DEBUG(10,("lookup on Domain SID\n"));
1392 getuseraliasntnam(sam_pass->nt_name, &mem_grp, &num_rids);
1393 unbecome_root(True);
1397 status = 0xC0000000 | NT_STATUS_NO_SUCH_USER;
1401 if (status == 0x0 && num_rids > 0)
1403 rid = malloc(num_rids * sizeof(uint32));
1404 if (mem_grp != NULL && rid != NULL)
1407 for (i = 0; i < num_rids; i++)
1409 rid[i] = mem_grp[i].rid;
1415 make_samr_r_query_useraliases(&r_u, num_rids, rid, status);
1417 /* store the response in the SMB stream */
1418 samr_io_r_query_useraliases("", &r_u, rdata, 0);
1425 DEBUG(5,("samr_query_useraliases: %d\n", __LINE__));
1429 /*******************************************************************
1430 api_samr_query_useraliases
1431 ********************************************************************/
1432 static void api_samr_query_useraliases( pipes_struct *p, prs_struct *data, prs_struct *rdata)
1434 SAMR_Q_QUERY_USERALIASES q_u;
1435 samr_io_q_query_useraliases("", &q_u, data, 0);
1436 samr_reply_query_useraliases(&q_u, rdata);
1437 samr_free_q_query_useraliases(&q_u);
1440 /*******************************************************************
1441 samr_reply_delete_dom_alias
1442 ********************************************************************/
1443 static void samr_reply_delete_dom_alias(SAMR_Q_DELETE_DOM_ALIAS *q_u,
1450 fstring alias_sid_str;
1452 SAMR_R_DELETE_DOM_ALIAS r_u;
1454 DEBUG(5,("samr_delete_dom_alias: %d\n", __LINE__));
1456 /* find the policy handle. open a policy on it. */
1457 if (status == 0x0 && !get_lsa_policy_samr_sid(&q_u->alias_pol, &alias_sid))
1459 status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
1463 sid_to_string(alias_sid_str, &alias_sid );
1464 sid_split_rid(&alias_sid, &alias_rid);
1469 DEBUG(10,("sid is %s\n", alias_sid_str));
1471 if (sid_equal(&alias_sid, &global_sam_sid))
1473 DEBUG(10,("lookup on Domain SID\n"));
1476 status = del_alias_entry(alias_rid) ? 0x0 : (0xC0000000 | NT_STATUS_NO_SUCH_ALIAS);
1477 unbecome_root(True);
1481 status = 0xC0000000 | NT_STATUS_NO_SUCH_ALIAS;
1485 make_samr_r_delete_dom_alias(&r_u, status);
1487 /* store the response in the SMB stream */
1488 samr_io_r_delete_dom_alias("", &r_u, rdata, 0);
1491 /*******************************************************************
1492 api_samr_delete_dom_alias
1493 ********************************************************************/
1494 static void api_samr_delete_dom_alias( pipes_struct *p, prs_struct *data, prs_struct *rdata)
1496 SAMR_Q_DELETE_DOM_ALIAS q_u;
1497 samr_io_q_delete_dom_alias("", &q_u, data, 0);
1498 samr_reply_delete_dom_alias(&q_u, rdata);
1502 /*******************************************************************
1503 samr_reply_query_aliasmem
1504 ********************************************************************/
1505 static void samr_reply_query_aliasmem(SAMR_Q_QUERY_ALIASMEM *q_u,
1510 LOCAL_GRP_MEMBER *mem_grp = NULL;
1511 DOM_SID2 *sid = NULL;
1515 fstring alias_sid_str;
1517 SAMR_R_QUERY_ALIASMEM r_u;
1519 DEBUG(5,("samr_query_aliasmem: %d\n", __LINE__));
1521 /* find the policy handle. open a policy on it. */
1522 if (status == 0x0 && !get_lsa_policy_samr_sid(&q_u->alias_pol, &alias_sid))
1524 status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
1528 sid_to_string(alias_sid_str, &alias_sid );
1529 sid_split_rid(&alias_sid, &alias_rid);
1534 DEBUG(10,("sid is %s\n", alias_sid_str));
1536 if (sid_equal(&alias_sid, &global_sid_S_1_5_20))
1538 DEBUG(10,("lookup on S-1-5-20\n"));
1541 status = getbuiltinrid(alias_rid, &mem_grp, &num_sids) != NULL ? 0x0 : 0xC0000000 | NT_STATUS_NO_SUCH_ALIAS;
1542 unbecome_root(True);
1544 else if (sid_equal(&alias_sid, &global_sam_sid))
1546 DEBUG(10,("lookup on Domain SID\n"));
1549 status = getaliasrid(alias_rid, &mem_grp, &num_sids) != NULL ? 0x0 : 0xC0000000 | NT_STATUS_NO_SUCH_ALIAS;
1550 unbecome_root(True);
1554 status = 0xC0000000 | NT_STATUS_NO_SUCH_ALIAS;
1558 if (status == 0x0 && num_sids > 0)
1560 sid = malloc(num_sids * sizeof(DOM_SID));
1561 if (mem_grp != NULL && sid != NULL)
1564 for (i = 0; i < num_sids; i++)
1566 make_dom_sid2(&sid[i], &mem_grp[i].sid);
1572 make_samr_r_query_aliasmem(&r_u, num_sids, sid, status);
1574 /* store the response in the SMB stream */
1575 samr_io_r_query_aliasmem("", &r_u, rdata, 0);
1582 DEBUG(5,("samr_query_aliasmem: %d\n", __LINE__));
1586 /*******************************************************************
1587 api_samr_query_aliasmem
1588 ********************************************************************/
1589 static void api_samr_query_aliasmem( pipes_struct *p, prs_struct *data, prs_struct *rdata)
1591 SAMR_Q_QUERY_ALIASMEM q_u;
1592 samr_io_q_query_aliasmem("", &q_u, data, 0);
1593 samr_reply_query_aliasmem(&q_u, rdata);
1596 /*******************************************************************
1597 samr_reply_lookup_names
1598 ********************************************************************/
1599 static void samr_reply_lookup_names(SAMR_Q_LOOKUP_NAMES *q_u,
1602 uint32 rid [MAX_SAM_ENTRIES];
1603 uint8 type[MAX_SAM_ENTRIES];
1606 int num_rids = q_u->num_names1;
1609 SAMR_R_LOOKUP_NAMES r_u;
1611 DEBUG(5,("samr_lookup_names: %d\n", __LINE__));
1613 if (status == 0x0 && !get_lsa_policy_samr_sid(&q_u->pol, &pol_sid))
1615 status = 0xC0000000 | NT_STATUS_OBJECT_TYPE_MISMATCH;
1618 if (num_rids > MAX_SAM_ENTRIES)
1620 num_rids = MAX_SAM_ENTRIES;
1621 DEBUG(5,("samr_lookup_names: truncating entries to %d\n", num_rids));
1624 SMB_ASSERT_ARRAY(q_u->uni_name, num_rids);
1626 for (i = 0; i < num_rids && status == 0; i++)
1630 unistr2_to_ascii(name, &q_u->uni_name[i], sizeof(name)-1);
1632 status = lookup_name(name, &sid, &(type[i]));
1635 sid_split_rid(&sid, &rid[i]);
1639 type[i] = SID_NAME_UNKNOWN;
1640 rid [i] = 0xffffffff;
1642 if (!sid_equal(&pol_sid, &sid))
1644 rid [i] = 0xffffffff;
1645 type[i] = SID_NAME_UNKNOWN;
1649 make_samr_r_lookup_names(&r_u, num_rids, rid, type, status);
1651 /* store the response in the SMB stream */
1652 samr_io_r_lookup_names("", &r_u, rdata, 0);
1654 DEBUG(5,("samr_lookup_names: %d\n", __LINE__));
1658 /*******************************************************************
1659 api_samr_lookup_names
1660 ********************************************************************/
1661 static void api_samr_lookup_names( pipes_struct *p, prs_struct *data, prs_struct *rdata)
1663 SAMR_Q_LOOKUP_NAMES q_u;
1664 samr_io_q_lookup_names("", &q_u, data, 0);
1665 samr_reply_lookup_names(&q_u, rdata);
1668 /*******************************************************************
1669 samr_reply_chgpasswd_user
1670 ********************************************************************/
1671 static void samr_reply_chgpasswd_user(SAMR_Q_CHGPASSWD_USER *q_u,
1674 SAMR_R_CHGPASSWD_USER r_u;
1675 uint32 status = 0x0;
1679 unistr2_to_ascii(user_name, &q_u->uni_user_name, sizeof(user_name)-1);
1680 unistr2_to_ascii(wks, &q_u->uni_dest_host, sizeof(wks)-1);
1682 DEBUG(5,("samr_chgpasswd_user: user: %s wks: %s\n", user_name, wks));
1684 if (!pass_oem_change(user_name,
1685 q_u->lm_newpass.pass, q_u->lm_oldhash.hash,
1686 q_u->nt_newpass.pass, q_u->nt_oldhash.hash))
1688 status = 0xC0000000 | NT_STATUS_WRONG_PASSWORD;
1691 make_samr_r_chgpasswd_user(&r_u, status);
1693 /* store the response in the SMB stream */
1694 samr_io_r_chgpasswd_user("", &r_u, rdata, 0);
1696 DEBUG(5,("samr_chgpasswd_user: %d\n", __LINE__));
1699 /*******************************************************************
1700 api_samr_chgpasswd_user
1701 ********************************************************************/
1702 static void api_samr_chgpasswd_user( pipes_struct *p, prs_struct *data, prs_struct *rdata)
1704 SAMR_Q_CHGPASSWD_USER q_u;
1705 samr_io_q_chgpasswd_user("", &q_u, data, 0);
1706 samr_reply_chgpasswd_user(&q_u, rdata);
1710 /*******************************************************************
1711 samr_reply_unknown_38
1712 ********************************************************************/
1713 static void samr_reply_unknown_38(SAMR_Q_UNKNOWN_38 *q_u,
1716 SAMR_R_UNKNOWN_38 r_u;
1718 DEBUG(5,("samr_unknown_38: %d\n", __LINE__));
1720 make_samr_r_unknown_38(&r_u);
1722 /* store the response in the SMB stream */
1723 samr_io_r_unknown_38("", &r_u, rdata, 0);
1725 DEBUG(5,("samr_unknown_38: %d\n", __LINE__));
1728 /*******************************************************************
1730 ********************************************************************/
1731 static void api_samr_unknown_38( pipes_struct *p, prs_struct *data, prs_struct *rdata)
1733 SAMR_Q_UNKNOWN_38 q_u;
1734 samr_io_q_unknown_38("", &q_u, data, 0);
1735 samr_reply_unknown_38(&q_u, rdata);
1739 /*******************************************************************
1740 samr_reply_lookup_rids
1741 ********************************************************************/
1742 static void samr_reply_lookup_rids(SAMR_Q_LOOKUP_RIDS *q_u,
1745 fstring group_names[MAX_SAM_ENTRIES];
1746 uint8 group_attrs[MAX_SAM_ENTRIES];
1748 int num_rids = q_u->num_rids1;
1751 SAMR_R_LOOKUP_RIDS r_u;
1754 DEBUG(5,("samr_lookup_rids: %d\n", __LINE__));
1756 /* find the policy handle. open a policy on it. */
1757 if (status == 0x0 && (find_lsa_policy_by_hnd(&(q_u->pol)) == -1))
1759 status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
1762 if (status == 0x0 && !get_lsa_policy_samr_sid(&q_u->pol, &pol_sid))
1764 status = 0xC0000000 | NT_STATUS_OBJECT_TYPE_MISMATCH;
1770 if (num_rids > MAX_SAM_ENTRIES)
1772 num_rids = MAX_SAM_ENTRIES;
1773 DEBUG(5,("samr_lookup_rids: truncating entries to %d\n", num_rids));
1776 for (i = 0; i < num_rids && status == 0; i++)
1779 sid_copy(&sid, &pol_sid);
1780 sid_append_rid(&sid, q_u->rid[i]);
1781 lookup_sid(&sid, group_names[i], &group_attrs[i]);
1785 make_samr_r_lookup_rids(&r_u, num_rids, group_names, group_attrs, status);
1787 /* store the response in the SMB stream */
1788 samr_io_r_lookup_rids("", &r_u, rdata, 0);
1790 DEBUG(5,("samr_lookup_rids: %d\n", __LINE__));
1794 /*******************************************************************
1795 api_samr_lookup_rids
1796 ********************************************************************/
1797 static void api_samr_lookup_rids( pipes_struct *p, prs_struct *data, prs_struct *rdata)
1799 SAMR_Q_LOOKUP_RIDS q_u;
1800 samr_io_q_lookup_rids("", &q_u, data, 0);
1801 samr_reply_lookup_rids(&q_u, rdata);
1802 samr_free_q_lookup_rids(&q_u);
1806 /*******************************************************************
1807 samr_reply_open_user
1808 ********************************************************************/
1809 static void samr_reply_open_user(SAMR_Q_OPEN_USER *q_u,
1813 SAMR_R_OPEN_USER r_u;
1814 struct sam_passwd *sam_pass;
1815 BOOL pol_open = False;
1817 /* set up the SAMR open_user response */
1818 bzero(r_u.user_pol.data, POL_HND_SIZE);
1822 /* find the policy handle. open a policy on it. */
1823 if (r_u.status == 0x0 && (find_lsa_policy_by_hnd(&(q_u->domain_pol)) == -1))
1825 r_u.status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
1828 /* get a (unique) handle. open a policy on it. */
1829 if (r_u.status == 0x0 && !(pol_open = open_lsa_policy_hnd(&(r_u.user_pol))))
1831 r_u.status = 0xC0000000 | NT_STATUS_OBJECT_NAME_NOT_FOUND;
1835 sam_pass = getsam21pwrid(q_u->user_rid);
1836 unbecome_root(True);
1838 /* check that the RID exists in our domain. */
1839 if (r_u.status == 0x0 && sam_pass == NULL)
1841 r_u.status = 0xC0000000 | NT_STATUS_NO_SUCH_USER;
1844 /* associate the RID with the (unique) handle. */
1845 if (r_u.status == 0x0 && !set_lsa_policy_samr_rid(&(r_u.user_pol), q_u->user_rid))
1847 /* oh, whoops. don't know what error message to return, here */
1848 r_u.status = 0xC0000000 | NT_STATUS_OBJECT_NAME_NOT_FOUND;
1851 if (r_u.status != 0 && pol_open)
1853 close_lsa_policy_hnd(&(r_u.user_pol));
1856 DEBUG(5,("samr_open_user: %d\n", __LINE__));
1858 /* store the response in the SMB stream */
1859 samr_io_r_open_user("", &r_u, rdata, 0);
1861 DEBUG(5,("samr_open_user: %d\n", __LINE__));
1865 /*******************************************************************
1867 ********************************************************************/
1868 static void api_samr_open_user( pipes_struct *p, prs_struct *data, prs_struct *rdata)
1870 SAMR_Q_OPEN_USER q_u;
1871 samr_io_q_open_user("", &q_u, data, 0);
1872 samr_reply_open_user(&q_u, rdata, 0x0);
1876 /*************************************************************************
1878 *************************************************************************/
1879 static BOOL get_user_info_10(SAM_USER_INFO_10 *id10, uint32 user_rid)
1881 struct sam_passwd *sam_pass;
1884 sam_pass = getsam21pwrid(user_rid);
1885 unbecome_root(True);
1887 if (sam_pass == NULL)
1889 DEBUG(4,("User 0x%x not found\n", user_rid));
1893 DEBUG(3,("User:[%s]\n", sam_pass->nt_name));
1895 make_sam_user_info10(id10, sam_pass->acct_ctrl);
1900 /*************************************************************************
1902 *************************************************************************/
1903 static BOOL get_user_info_21(SAM_USER_INFO_21 *id21, uint32 user_rid)
1905 struct sam_passwd *sam_pass;
1910 sam_pass = getsam21pwrid(user_rid);
1911 unbecome_root(True);
1913 if (sam_pass == NULL)
1915 DEBUG(4,("User 0x%x not found\n", user_rid));
1919 DEBUG(3,("User:[%s]\n", sam_pass->nt_name));
1921 /* create a LOGON_HRS structure */
1922 hrs.len = sam_pass->hours_len;
1923 SMB_ASSERT_ARRAY(hrs.hours, hrs.len);
1924 for (i = 0; i < hrs.len; i++)
1926 hrs.hours[i] = sam_pass->hours[i];
1929 make_sam_user_info21(id21,
1931 &sam_pass->logon_time,
1932 &sam_pass->logoff_time,
1933 &sam_pass->kickoff_time,
1934 &sam_pass->pass_last_set_time,
1935 &sam_pass->pass_can_change_time,
1936 &sam_pass->pass_must_change_time,
1938 sam_pass->nt_name, /* user_name */
1939 sam_pass->full_name, /* full_name */
1940 sam_pass->home_dir, /* home_dir */
1941 sam_pass->dir_drive, /* dir_drive */
1942 sam_pass->logon_script, /* logon_script */
1943 sam_pass->profile_path, /* profile_path */
1944 sam_pass->acct_desc, /* description */
1945 sam_pass->workstations, /* workstations user can log in from */
1946 sam_pass->unknown_str, /* don't know, yet */
1947 sam_pass->munged_dial, /* dialin info. contains dialin path and tel no */
1949 sam_pass->user_rid, /* RID user_id */
1950 sam_pass->group_rid, /* RID group_id */
1951 sam_pass->acct_ctrl,
1953 sam_pass->unknown_3, /* unknown_3 */
1954 sam_pass->logon_divs, /* divisions per week */
1955 &hrs, /* logon hours */
1956 sam_pass->unknown_5,
1957 sam_pass->unknown_6);
1962 /*******************************************************************
1963 samr_reply_query_userinfo
1964 ********************************************************************/
1965 static void samr_reply_query_userinfo(SAMR_Q_QUERY_USERINFO *q_u,
1968 SAMR_R_QUERY_USERINFO r_u;
1970 SAM_USER_INFO_11 id11;
1972 SAM_USER_INFO_10 id10;
1973 SAM_USER_INFO_21 id21;
1976 uint32 status = 0x0;
1979 DEBUG(5,("samr_reply_query_userinfo: %d\n", __LINE__));
1981 /* search for the handle */
1982 if (status == 0x0 && (find_lsa_policy_by_hnd(&(q_u->pol)) == -1))
1984 status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
1987 /* find the user's rid */
1988 if (status == 0x0 && (rid = get_lsa_policy_samr_rid(&(q_u->pol))) == 0xffffffff)
1990 status = 0xC0000000 | NT_STATUS_OBJECT_TYPE_MISMATCH;
1993 DEBUG(5,("samr_reply_query_userinfo: rid:0x%x\n", rid));
1995 /* ok! user info levels (there are lots: see MSDEV help), off we go... */
1998 switch (q_u->switch_value)
2002 info = (void*)&id10;
2003 status = get_user_info_10(&id10, rid) ? 0 : (0xC0000000 | NT_STATUS_NO_SUCH_USER);
2007 /* whoops - got this wrong. i think. or don't understand what's happening. */
2011 info = (void*)&id11;
2013 expire.low = 0xffffffff;
2014 expire.high = 0x7fffffff;
2016 make_sam_user_info11(&id11, &expire, "BROOKFIELDS$", 0x03ef, 0x201, 0x0080);
2023 info = (void*)&id21;
2024 status = get_user_info_21(&id21, rid) ? 0 : (0xC0000000 | NT_STATUS_NO_SUCH_USER);
2030 status = 0xC0000000 | NT_STATUS_INVALID_INFO_CLASS;
2037 make_samr_r_query_userinfo(&r_u, q_u->switch_value, info, status);
2039 /* store the response in the SMB stream */
2040 samr_io_r_query_userinfo("", &r_u, rdata, 0);
2042 DEBUG(5,("samr_reply_query_userinfo: %d\n", __LINE__));
2046 /*******************************************************************
2048 ********************************************************************/
2049 static BOOL set_user_info_24(SAM_USER_INFO_24 *id24, uint32 rid)
2051 struct sam_passwd *pwd = getsam21pwrid(rid);
2052 struct sam_passwd new_pwd;
2053 static uchar nt_hash[16];
2054 static uchar lm_hash[16];
2063 pwdb_init_sam(&new_pwd);
2064 copy_sam_passwd(&new_pwd, pwd);
2066 if (!decode_pw_buffer(id24->pass, (char *)new_pw.buffer, 256, &len))
2071 new_pw.uni_max_len = len / 2;
2072 new_pw.uni_str_len = len / 2;
2074 nt_lm_owf_genW(&new_pw, nt_hash, lm_hash);
2076 new_pwd.smb_passwd = lm_hash;
2077 new_pwd.smb_nt_passwd = nt_hash;
2079 return mod_sam21pwd_entry(&new_pwd, True);
2082 /*******************************************************************
2084 ********************************************************************/
2085 static BOOL set_user_info_23(SAM_USER_INFO_23 *id23, uint32 rid)
2087 struct sam_passwd *pwd = getsam21pwrid(rid);
2088 struct sam_passwd new_pwd;
2089 static uchar nt_hash[16];
2090 static uchar lm_hash[16];
2096 DEBUG(5, ("set_user_info_23: NULL id23\n"));
2104 pwdb_init_sam(&new_pwd);
2105 copy_sam_passwd(&new_pwd, pwd);
2106 copy_id23_to_sam_passwd(&new_pwd, id23);
2108 if (!decode_pw_buffer(id23->pass, (char*)new_pw.buffer, 256, &len))
2113 new_pw.uni_max_len = len / 2;
2114 new_pw.uni_str_len = len / 2;
2116 nt_lm_owf_genW(&new_pw, nt_hash, lm_hash);
2118 new_pwd.smb_passwd = lm_hash;
2119 new_pwd.smb_nt_passwd = nt_hash;
2121 return mod_sam21pwd_entry(&new_pwd, True);
2124 /*******************************************************************
2126 ********************************************************************/
2127 static BOOL set_user_info_16(SAM_USER_INFO_16 *id16, uint32 rid)
2129 struct sam_passwd *pwd = getsam21pwrid(rid);
2130 struct sam_passwd new_pwd;
2134 DEBUG(5, ("set_user_info_16: NULL id16\n"));
2142 copy_sam_passwd(&new_pwd, pwd);
2144 new_pwd.acct_ctrl = id16->acb_info;
2146 return mod_sam21pwd_entry(&new_pwd, True);
2149 /*******************************************************************
2150 api_samr_query_userinfo
2151 ********************************************************************/
2152 static void api_samr_query_userinfo( pipes_struct *p, prs_struct *data, prs_struct *rdata)
2154 SAMR_Q_QUERY_USERINFO q_u;
2155 samr_io_q_query_userinfo("", &q_u, data, 0);
2156 samr_reply_query_userinfo(&q_u, rdata);
2160 /*******************************************************************
2161 samr_reply_set_userinfo2
2162 ********************************************************************/
2163 static void samr_reply_set_userinfo2(SAMR_Q_SET_USERINFO2 *q_u,
2164 prs_struct *rdata, uchar user_sess_key[16])
2166 SAMR_R_SET_USERINFO2 r_u;
2168 uint32 status = 0x0;
2171 DEBUG(5,("samr_reply_set_userinfo2: %d\n", __LINE__));
2173 /* search for the handle */
2174 if (status == 0x0 && (find_lsa_policy_by_hnd(&(q_u->pol)) == -1))
2176 status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
2179 /* find the user's rid */
2180 if (status == 0x0 && (rid = get_lsa_policy_samr_rid(&(q_u->pol))) == 0xffffffff)
2182 status = 0xC0000000 | NT_STATUS_OBJECT_TYPE_MISMATCH;
2185 DEBUG(5,("samr_reply_set_userinfo2: rid:0x%x\n", rid));
2187 /* ok! user info levels (there are lots: see MSDEV help), off we go... */
2188 if (status == 0x0 && q_u->info.id == NULL)
2190 DEBUG(5,("samr_reply_set_userinfo2: NULL info level\n"));
2191 status = 0xC0000000 | NT_STATUS_INVALID_INFO_CLASS;
2196 switch (q_u->switch_value)
2200 SAM_USER_INFO_16 *id16 = q_u->info.id16;
2201 status = set_user_info_16(id16, rid) ? 0 : (0xC0000000 | NT_STATUS_ACCESS_DENIED);
2206 status = 0xC0000000 | NT_STATUS_INVALID_INFO_CLASS;
2213 make_samr_r_set_userinfo2(&r_u, status);
2215 /* store the response in the SMB stream */
2216 samr_io_r_set_userinfo2("", &r_u, rdata, 0);
2218 DEBUG(5,("samr_reply_set_userinfo2: %d\n", __LINE__));
2222 /*******************************************************************
2223 api_samr_set_userinfo2
2224 ********************************************************************/
2225 static void api_samr_set_userinfo2( pipes_struct *p, prs_struct *data, prs_struct *rdata)
2227 user_struct *vuser = get_valid_user_struct(p->vuid);
2228 SAMR_Q_SET_USERINFO2 q_u;
2231 samr_io_q_set_userinfo2("", &q_u, data, 0);
2232 samr_reply_set_userinfo2(&q_u, rdata, vuser->dc.user_sess_key);
2234 if (q_u.info.id != NULL)
2241 /*******************************************************************
2242 samr_reply_set_userinfo
2243 ********************************************************************/
2244 static void samr_reply_set_userinfo(SAMR_Q_SET_USERINFO *q_u,
2245 prs_struct *rdata, uchar user_sess_key[16])
2247 SAMR_R_SET_USERINFO r_u;
2249 uint32 status = 0x0;
2252 DEBUG(5,("samr_reply_set_userinfo: %d\n", __LINE__));
2254 /* search for the handle */
2255 if (status == 0x0 && (find_lsa_policy_by_hnd(&(q_u->pol)) == -1))
2257 status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
2260 /* find the user's rid */
2261 if (status == 0x0 && (rid = get_lsa_policy_samr_rid(&(q_u->pol))) == 0xffffffff)
2263 status = 0xC0000000 | NT_STATUS_OBJECT_TYPE_MISMATCH;
2266 DEBUG(5,("samr_reply_set_userinfo: rid:0x%x\n", rid));
2268 /* ok! user info levels (there are lots: see MSDEV help), off we go... */
2269 if (status == 0x0 && q_u->info.id == NULL)
2271 DEBUG(5,("samr_reply_set_userinfo: NULL info level\n"));
2272 status = 0xC0000000 | NT_STATUS_INVALID_INFO_CLASS;
2277 switch (q_u->switch_value)
2281 SAM_USER_INFO_24 *id24 = q_u->info.id24;
2282 SamOEMhash(id24->pass, user_sess_key, True);
2283 status = set_user_info_24(id24, rid) ? 0 : (0xC0000000 | NT_STATUS_ACCESS_DENIED);
2289 SAM_USER_INFO_23 *id23 = q_u->info.id23;
2290 SamOEMhash(id23->pass, user_sess_key, 1);
2292 DEBUG(100,("pass buff:\n"));
2293 dump_data(100, id23->pass, sizeof(id23->pass));
2297 status = set_user_info_23(id23, rid) ? 0 : (0xC0000000 | NT_STATUS_ACCESS_DENIED);
2303 status = 0xC0000000 | NT_STATUS_INVALID_INFO_CLASS;
2310 make_samr_r_set_userinfo(&r_u, status);
2312 /* store the response in the SMB stream */
2313 samr_io_r_set_userinfo("", &r_u, rdata, 0);
2315 DEBUG(5,("samr_reply_set_userinfo: %d\n", __LINE__));
2319 /*******************************************************************
2320 api_samr_set_userinfo
2321 ********************************************************************/
2322 static void api_samr_set_userinfo( pipes_struct *p, prs_struct *data, prs_struct *rdata)
2324 user_struct *vuser = get_valid_user_struct(p->vuid);
2325 SAMR_Q_SET_USERINFO q_u;
2328 #ifdef DEBUG_PASSWORD
2329 DEBUG(100,("set user info: sess_key: "));
2330 dump_data(100, vuser->dc.user_sess_key, 16);
2332 samr_io_q_set_userinfo("", &q_u, data, 0);
2333 samr_reply_set_userinfo(&q_u, rdata, vuser->dc.user_sess_key);
2335 if (q_u.info.id != NULL)
2342 /*******************************************************************
2343 samr_reply_query_usergroups
2344 ********************************************************************/
2345 static void samr_reply_query_usergroups(SAMR_Q_QUERY_USERGROUPS *q_u,
2348 SAMR_R_QUERY_USERGROUPS r_u;
2349 uint32 status = 0x0;
2351 struct sam_passwd *sam_pass;
2352 DOM_GID *gids = NULL;
2356 DEBUG(5,("samr_query_usergroups: %d\n", __LINE__));
2358 /* find the policy handle. open a policy on it. */
2359 if (status == 0x0 && (find_lsa_policy_by_hnd(&(q_u->pol)) == -1))
2361 status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
2364 /* find the user's rid */
2365 if (status == 0x0 && (rid = get_lsa_policy_samr_rid(&(q_u->pol))) == 0xffffffff)
2367 status = 0xC0000000 | NT_STATUS_OBJECT_TYPE_MISMATCH;
2373 sam_pass = getsam21pwrid(rid);
2374 unbecome_root(True);
2376 if (sam_pass == NULL)
2378 status = 0xC0000000 | NT_STATUS_NO_SUCH_USER;
2384 DOMAIN_GRP *mem_grp = NULL;
2387 getusergroupsntnam(sam_pass->nt_name, &mem_grp, &num_groups);
2388 unbecome_root(True);
2391 num_groups = make_dom_gids(mem_grp, num_groups, &gids);
2393 if (mem_grp != NULL)
2399 /* construct the response. lkclXXXX: gids are not copied! */
2400 make_samr_r_query_usergroups(&r_u, num_groups, gids, status);
2402 /* store the response in the SMB stream */
2403 samr_io_r_query_usergroups("", &r_u, rdata, 0);
2410 DEBUG(5,("samr_query_usergroups: %d\n", __LINE__));
2414 /*******************************************************************
2415 api_samr_query_usergroups
2416 ********************************************************************/
2417 static void api_samr_query_usergroups( pipes_struct *p, prs_struct *data, prs_struct *rdata)
2419 SAMR_Q_QUERY_USERGROUPS q_u;
2420 samr_io_q_query_usergroups("", &q_u, data, 0);
2421 samr_reply_query_usergroups(&q_u, rdata);
2425 /*******************************************************************
2426 opens a samr alias by rid, returns a policy handle.
2427 ********************************************************************/
2428 static uint32 open_samr_alias(DOM_SID *sid, POLICY_HND *alias_pol,
2431 BOOL pol_open = False;
2432 uint32 status = 0x0;
2434 /* get a (unique) handle. open a policy on it. */
2435 if (status == 0x0 && !(pol_open = open_lsa_policy_hnd(alias_pol)))
2437 status = 0xC0000000 | NT_STATUS_OBJECT_NAME_NOT_FOUND;
2440 DEBUG(0,("TODO: verify that the alias rid exists\n"));
2442 /* associate a RID with the (unique) handle. */
2443 if (status == 0x0 && !set_lsa_policy_samr_rid(alias_pol, alias_rid))
2445 /* oh, whoops. don't know what error message to return, here */
2446 status = 0xC0000000 | NT_STATUS_OBJECT_NAME_NOT_FOUND;
2449 sid_append_rid(sid, alias_rid);
2451 /* associate an alias SID with the (unique) handle. */
2452 if (status == 0x0 && !set_lsa_policy_samr_sid(alias_pol, sid))
2454 /* oh, whoops. don't know what error message to return, here */
2455 status = 0xC0000000 | NT_STATUS_OBJECT_NAME_NOT_FOUND;
2458 if (status != 0 && pol_open)
2460 close_lsa_policy_hnd(alias_pol);
2466 /*******************************************************************
2467 samr_reply_create_dom_alias
2468 ********************************************************************/
2469 static void samr_reply_create_dom_alias(SAMR_Q_CREATE_DOM_ALIAS *q_u,
2472 SAMR_R_CREATE_DOM_ALIAS r_u;
2475 POLICY_HND alias_pol;
2476 uint32 status = 0x0;
2478 bzero(&alias_pol, sizeof(alias_pol));
2480 DEBUG(5,("samr_create_dom_alias: %d\n", __LINE__));
2482 /* find the policy handle. open a policy on it. */
2483 if (status == 0x0 && (find_lsa_policy_by_hnd(&(q_u->dom_pol)) == -1))
2485 status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
2488 /* find the domain sid */
2489 if (status == 0x0 && !get_lsa_policy_samr_sid(&q_u->dom_pol, &dom_sid))
2491 status = 0xC0000000 | NT_STATUS_OBJECT_TYPE_MISMATCH;
2494 if (!sid_equal(&dom_sid, &global_sam_sid))
2496 status = 0xC0000000 | NT_STATUS_ACCESS_DENIED;
2501 unistr2_to_ascii(grp.name, &q_u->uni_acct_desc, sizeof(grp.name)-1);
2502 fstrcpy(grp.comment, "");
2503 grp.rid = 0xffffffff;
2506 status = add_alias_entry(&grp) ? 0 : (0xC0000000 | NT_STATUS_ACCESS_DENIED);
2507 unbecome_root(True);
2512 status = open_samr_alias(&dom_sid, &alias_pol, grp.rid);
2515 /* construct the response. */
2516 make_samr_r_create_dom_alias(&r_u, &alias_pol, grp.rid, status);
2518 /* store the response in the SMB stream */
2519 samr_io_r_create_dom_alias("", &r_u, rdata, 0);
2521 DEBUG(5,("samr_create_dom_alias: %d\n", __LINE__));
2525 /*******************************************************************
2526 api_samr_create_dom_alias
2527 ********************************************************************/
2528 static void api_samr_create_dom_alias( pipes_struct *p, prs_struct *data, prs_struct *rdata)
2530 SAMR_Q_CREATE_DOM_ALIAS q_u;
2531 samr_io_q_create_dom_alias("", &q_u, data, 0);
2532 samr_reply_create_dom_alias(&q_u, rdata);
2536 /*******************************************************************
2537 opens a samr group by rid, returns a policy handle.
2538 ********************************************************************/
2539 static uint32 open_samr_group(DOM_SID *sid, POLICY_HND *group_pol,
2542 BOOL pol_open = False;
2543 uint32 status = 0x0;
2545 /* get a (unique) handle. open a policy on it. */
2546 if (status == 0x0 && !(pol_open = open_lsa_policy_hnd(group_pol)))
2548 status = 0xC0000000 | NT_STATUS_OBJECT_NAME_NOT_FOUND;
2551 DEBUG(0,("TODO: verify that the group rid exists\n"));
2553 /* associate a RID with the (unique) handle. */
2554 if (status == 0x0 && !set_lsa_policy_samr_rid(group_pol, group_rid))
2556 /* oh, whoops. don't know what error message to return, here */
2557 status = 0xC0000000 | NT_STATUS_OBJECT_NAME_NOT_FOUND;
2560 sid_append_rid(sid, group_rid);
2562 /* associate an group SID with the (unique) handle. */
2563 if (status == 0x0 && !set_lsa_policy_samr_sid(group_pol, sid))
2565 /* oh, whoops. don't know what error message to return, here */
2566 status = 0xC0000000 | NT_STATUS_OBJECT_NAME_NOT_FOUND;
2569 if (status != 0 && pol_open)
2571 close_lsa_policy_hnd(group_pol);
2577 /*******************************************************************
2578 samr_reply_create_dom_group
2579 ********************************************************************/
2580 static void samr_reply_create_dom_group(SAMR_Q_CREATE_DOM_GROUP *q_u,
2583 SAMR_R_CREATE_DOM_GROUP r_u;
2586 POLICY_HND group_pol;
2587 uint32 status = 0x0;
2589 bzero(&group_pol, sizeof(group_pol));
2591 DEBUG(5,("samr_create_dom_group: %d\n", __LINE__));
2593 /* find the policy handle. open a policy on it. */
2594 if (status == 0x0 && (find_lsa_policy_by_hnd(&(q_u->pol)) == -1))
2596 status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
2599 /* find the domain sid */
2600 if (status == 0x0 && !get_lsa_policy_samr_sid(&q_u->pol, &dom_sid))
2602 status = 0xC0000000 | NT_STATUS_OBJECT_TYPE_MISMATCH;
2605 if (!sid_equal(&dom_sid, &global_sam_sid))
2607 status = 0xC0000000 | NT_STATUS_ACCESS_DENIED;
2612 unistr2_to_ascii(grp.name, &q_u->uni_acct_desc, sizeof(grp.name)-1);
2613 fstrcpy(grp.comment, "");
2614 grp.rid = 0xffffffff;
2618 status = add_group_entry(&grp) ? 0x0 : (0xC0000000 | NT_STATUS_ACCESS_DENIED);
2619 unbecome_root(True);
2624 status = open_samr_group(&dom_sid, &group_pol, grp.rid);
2627 /* construct the response. */
2628 make_samr_r_create_dom_group(&r_u, &group_pol, grp.rid, status);
2630 /* store the response in the SMB stream */
2631 samr_io_r_create_dom_group("", &r_u, rdata, 0);
2633 DEBUG(5,("samr_create_dom_group: %d\n", __LINE__));
2637 /*******************************************************************
2638 api_samr_create_dom_group
2639 ********************************************************************/
2640 static void api_samr_create_dom_group( pipes_struct *p, prs_struct *data, prs_struct *rdata)
2642 SAMR_Q_CREATE_DOM_GROUP q_u;
2643 samr_io_q_create_dom_group("", &q_u, data, 0);
2644 samr_reply_create_dom_group(&q_u, rdata);
2648 /*******************************************************************
2649 samr_reply_query_dom_info
2650 ********************************************************************/
2651 static void samr_reply_query_dom_info(SAMR_Q_QUERY_DOMAIN_INFO *q_u,
2654 SAMR_R_QUERY_DOMAIN_INFO r_u;
2656 uint16 switch_value = 0x0;
2657 uint32 status = 0x0;
2664 DEBUG(5,("samr_reply_query_dom_info: %d\n", __LINE__));
2666 /* find the policy handle. open a policy on it. */
2667 if (r_u.status == 0x0 && (find_lsa_policy_by_hnd(&(q_u->domain_pol)) == -1))
2669 r_u.status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
2670 DEBUG(5,("samr_reply_query_dom_info: invalid handle\n"));
2675 switch (q_u->switch_value)
2680 make_unk_info7(&ctr.info.inf7);
2687 make_unk_info6(&ctr.info.inf6);
2694 make_unk_info3(&ctr.info.inf3);
2701 make_unk_info2(&ctr.info.inf2, global_sam_name, global_myname);
2708 make_unk_info1(&ctr.info.inf1);
2714 status = 0xC0000000 | NT_STATUS_INVALID_INFO_CLASS;
2720 make_samr_r_query_dom_info(&r_u, switch_value, &ctr, status);
2722 /* store the response in the SMB stream */
2723 samr_io_r_query_dom_info("", &r_u, rdata, 0);
2725 DEBUG(5,("samr_query_dom_info: %d\n", __LINE__));
2729 /*******************************************************************
2730 api_samr_query_dom_info
2731 ********************************************************************/
2732 static void api_samr_query_dom_info( pipes_struct *p, prs_struct *data, prs_struct *rdata)
2734 SAMR_Q_QUERY_DOMAIN_INFO q_e;
2735 samr_io_q_query_dom_info("", &q_e, data, 0);
2736 samr_reply_query_dom_info(&q_e, rdata);
2741 /*******************************************************************
2742 samr_reply_create_user
2743 ********************************************************************/
2744 static void samr_reply_create_user(SAMR_Q_CREATE_USER *q_u,
2747 struct sam_passwd *sam_pass;
2750 SAMR_R_CREATE_USER r_u;
2752 uint32 status = 0x0;
2753 uint32 user_rid = 0x0;
2754 BOOL pol_open = False;
2755 uint32 unk_0 = 0x30;
2757 /* find the machine account: tell the caller if it exists.
2758 lkclXXXX i have *no* idea if this is a problem or not
2759 or even if you are supposed to construct a different
2760 reply if the account already exists...
2763 /* find the policy handle. open a policy on it. */
2764 if (status == 0x0 && (find_lsa_policy_by_hnd(&(q_u->domain_pol)) == -1))
2766 status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
2769 /* get a (unique) handle. open a policy on it. */
2770 if (status == 0x0 && !(pol_open = open_lsa_policy_hnd(&pol)))
2772 status = 0xC0000000 | NT_STATUS_OBJECT_NAME_NOT_FOUND;
2775 unistr2_to_ascii(user_name, &q_u->uni_name, sizeof(user_name)-1);
2777 sam_pass = getsam21pwntnam(user_name);
2779 if (sam_pass != NULL)
2781 /* account exists: say so */
2782 status = 0xC0000000 | NT_STATUS_USER_EXISTS;
2789 if (!local_password_change(user_name, True,
2790 q_u->acb_info | ACB_DISABLED | ACB_PWNOTREQ, 0xffff,
2792 err_str, sizeof(err_str),
2793 msg_str, sizeof(msg_str)))
2795 DEBUG(0,("%s\n", err_str));
2796 status = 0xC0000000 | NT_STATUS_ACCESS_DENIED;
2800 sam_pass = getsam21pwntnam(user_name);
2801 if (sam_pass == NULL)
2803 /* account doesn't exist: say so */
2804 status = 0xC0000000 | NT_STATUS_ACCESS_DENIED;
2808 user_rid = sam_pass->user_rid;
2814 /* associate the RID with the (unique) handle. */
2815 if (status == 0x0 && !set_lsa_policy_samr_rid(&pol, user_rid))
2817 /* oh, whoops. don't know what error message to return, here */
2818 status = 0xC0000000 | NT_STATUS_OBJECT_NAME_NOT_FOUND;
2821 if (status != 0 && pol_open)
2823 close_lsa_policy_hnd(&pol);
2826 DEBUG(5,("samr_create_user: %d\n", __LINE__));
2828 make_samr_r_create_user(&r_u, &pol, unk_0, user_rid, status);
2830 /* store the response in the SMB stream */
2831 samr_io_r_create_user("", &r_u, rdata, 0);
2833 DEBUG(5,("samr_create_user: %d\n", __LINE__));
2837 /*******************************************************************
2838 api_samr_create_user
2839 ********************************************************************/
2840 static void api_samr_create_user( pipes_struct *p, prs_struct *data, prs_struct *rdata)
2842 SAMR_Q_CREATE_USER q_u;
2844 /* grab the samr unknown 32 */
2845 samr_io_q_create_user("", &q_u, data, 0);
2847 /* construct reply. */
2848 samr_reply_create_user(&q_u, rdata);
2852 /*******************************************************************
2853 samr_reply_connect_anon
2854 ********************************************************************/
2855 static void samr_reply_connect_anon(SAMR_Q_CONNECT_ANON *q_u,
2858 SAMR_R_CONNECT_ANON r_u;
2859 BOOL pol_open = False;
2861 /* set up the SAMR connect_anon response */
2864 /* get a (unique) handle. open a policy on it. */
2865 if (r_u.status == 0x0 && !(pol_open = open_lsa_policy_hnd(&(r_u.connect_pol))))
2867 r_u.status = 0xC0000000 | NT_STATUS_OBJECT_NAME_NOT_FOUND;
2870 /* associate the domain SID with the (unique) handle. */
2871 if (r_u.status == 0x0 && !set_lsa_policy_samr_pol_status(&(r_u.connect_pol), q_u->unknown_0))
2873 /* oh, whoops. don't know what error message to return, here */
2874 r_u.status = 0xC0000000 | NT_STATUS_OBJECT_NAME_NOT_FOUND;
2877 if (r_u.status != 0 && pol_open)
2879 close_lsa_policy_hnd(&(r_u.connect_pol));
2882 DEBUG(5,("samr_connect_anon: %d\n", __LINE__));
2884 /* store the response in the SMB stream */
2885 samr_io_r_connect_anon("", &r_u, rdata, 0);
2887 DEBUG(5,("samr_connect_anon: %d\n", __LINE__));
2891 /*******************************************************************
2892 api_samr_connect_anon
2893 ********************************************************************/
2894 static void api_samr_connect_anon( pipes_struct *p, prs_struct *data, prs_struct *rdata)
2896 SAMR_Q_CONNECT_ANON q_u;
2897 samr_io_q_connect_anon("", &q_u, data, 0);
2898 samr_reply_connect_anon(&q_u, rdata);
2901 /*******************************************************************
2903 ********************************************************************/
2904 static void samr_reply_connect(SAMR_Q_CONNECT *q_u,
2908 BOOL pol_open = False;
2910 /* set up the SAMR connect response */
2913 /* get a (unique) handle. open a policy on it. */
2914 if (r_u.status == 0x0 && !(pol_open = open_lsa_policy_hnd(&(r_u.connect_pol))))
2916 r_u.status = 0xC0000000 | NT_STATUS_OBJECT_NAME_NOT_FOUND;
2919 /* associate the domain SID with the (unique) handle. */
2920 if (r_u.status == 0x0 && !set_lsa_policy_samr_pol_status(&(r_u.connect_pol), q_u->unknown_0))
2922 /* oh, whoops. don't know what error message to return, here */
2923 r_u.status = 0xC0000000 | NT_STATUS_OBJECT_NAME_NOT_FOUND;
2926 if (r_u.status != 0 && pol_open)
2928 close_lsa_policy_hnd(&(r_u.connect_pol));
2931 DEBUG(5,("samr_connect: %d\n", __LINE__));
2933 /* store the response in the SMB stream */
2934 samr_io_r_connect("", &r_u, rdata, 0);
2936 DEBUG(5,("samr_connect: %d\n", __LINE__));
2940 /*******************************************************************
2942 ********************************************************************/
2943 static void api_samr_connect( pipes_struct *p, prs_struct *data, prs_struct *rdata)
2946 samr_io_q_connect("", &q_u, data, 0);
2947 samr_reply_connect(&q_u, rdata);
2950 /*******************************************************************
2951 samr_reply_open_alias
2952 ********************************************************************/
2953 static void samr_reply_open_alias(SAMR_Q_OPEN_ALIAS *q_u,
2956 SAMR_R_OPEN_ALIAS r_u;
2958 BOOL pol_open = False;
2960 /* set up the SAMR open_alias response */
2963 if (r_u.status == 0x0 && !get_lsa_policy_samr_sid(&q_u->dom_pol, &sid))
2965 r_u.status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
2968 /* get a (unique) handle. open a policy on it. */
2969 if (r_u.status == 0x0 && !(pol_open = open_lsa_policy_hnd(&(r_u.pol))))
2971 r_u.status = 0xC0000000 | NT_STATUS_OBJECT_NAME_NOT_FOUND;
2974 DEBUG(0,("TODO: verify that the alias rid exists\n"));
2976 /* associate a RID with the (unique) handle. */
2977 if (r_u.status == 0x0 && !set_lsa_policy_samr_rid(&(r_u.pol), q_u->rid_alias))
2979 /* oh, whoops. don't know what error message to return, here */
2980 r_u.status = 0xC0000000 | NT_STATUS_OBJECT_NAME_NOT_FOUND;
2983 sid_append_rid(&sid, q_u->rid_alias);
2985 /* associate an alias SID with the (unique) handle. */
2986 if (r_u.status == 0x0 && !set_lsa_policy_samr_sid(&(r_u.pol), &sid))
2988 /* oh, whoops. don't know what error message to return, here */
2989 r_u.status = 0xC0000000 | NT_STATUS_OBJECT_NAME_NOT_FOUND;
2992 if (r_u.status != 0 && pol_open)
2994 close_lsa_policy_hnd(&(r_u.pol));
2997 DEBUG(5,("samr_open_alias: %d\n", __LINE__));
2999 /* store the response in the SMB stream */
3000 samr_io_r_open_alias("", &r_u, rdata, 0);
3002 DEBUG(5,("samr_open_alias: %d\n", __LINE__));
3006 /*******************************************************************
3008 ********************************************************************/
3009 static void api_samr_open_alias( pipes_struct *p, prs_struct *data, prs_struct *rdata)
3012 SAMR_Q_OPEN_ALIAS q_u;
3013 samr_io_q_open_alias("", &q_u, data, 0);
3014 samr_reply_open_alias(&q_u, rdata);
3017 /*******************************************************************
3018 samr_reply_open_group
3019 ********************************************************************/
3020 static void samr_reply_open_group(SAMR_Q_OPEN_GROUP *q_u,
3023 SAMR_R_OPEN_GROUP r_u;
3026 DEBUG(5,("samr_open_group: %d\n", __LINE__));
3030 /* find the domain sid associated with the policy handle */
3031 if (r_u.status == 0x0 && !get_lsa_policy_samr_sid(&q_u->domain_pol, &sid))
3033 r_u.status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
3036 if (r_u.status == 0x0 && !sid_equal(&sid, &global_sam_sid))
3038 r_u.status = 0xC0000000 | NT_STATUS_ACCESS_DENIED;
3041 if (r_u.status == 0x0)
3043 r_u.status = open_samr_group(&sid, &r_u.pol, q_u->rid_group);
3046 /* store the response in the SMB stream */
3047 samr_io_r_open_group("", &r_u, rdata, 0);
3049 DEBUG(5,("samr_open_group: %d\n", __LINE__));
3053 /*******************************************************************
3055 ********************************************************************/
3056 static void api_samr_open_group( pipes_struct *p, prs_struct *data, prs_struct *rdata)
3059 SAMR_Q_OPEN_GROUP q_u;
3060 samr_io_q_open_group("", &q_u, data, 0);
3061 samr_reply_open_group(&q_u, rdata);
3064 /*******************************************************************
3065 samr_reply_lookup_domain
3066 ********************************************************************/
3067 static void samr_reply_lookup_domain(SAMR_Q_LOOKUP_DOMAIN *q_u,
3070 SAMR_R_LOOKUP_DOMAIN r_u;
3073 DEBUG(5,("samr_lookup_domain: %d\n", __LINE__));
3078 /* find the connection policy handle */
3079 if (find_lsa_policy_by_hnd(&(q_u->connect_pol)) == -1)
3081 r_u.status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
3084 if (r_u.status == 0x0)
3086 unistr2_to_ascii(domain, &(q_u->uni_domain), sizeof(domain));
3087 DEBUG(5, ("Lookup Domain: %s\n", domain));
3089 /* check it's one of ours */
3090 if (strequal(domain, global_sam_name))
3092 make_dom_sid2(&(r_u.dom_sid), &global_sam_sid);
3095 else if (strequal(domain, "BUILTIN"))
3097 make_dom_sid2(&(r_u.dom_sid), &global_sid_S_1_5_20);
3102 r_u.status = 0xC0000000 | NT_STATUS_NO_SUCH_DOMAIN;
3106 /* store the response in the SMB stream */
3107 samr_io_r_lookup_domain("", &r_u, rdata, 0);
3109 DEBUG(5,("samr_lookup_domain: %d\n", __LINE__));
3112 /*******************************************************************
3113 api_samr_lookup_domain
3114 ********************************************************************/
3115 static void api_samr_lookup_domain( pipes_struct *p, prs_struct *data, prs_struct *rdata)
3117 SAMR_Q_LOOKUP_DOMAIN q_u;
3118 samr_io_q_lookup_domain("", &q_u, data, 0);
3119 samr_reply_lookup_domain(&q_u, rdata);
3122 /*******************************************************************
3123 array of \PIPE\samr operations
3124 ********************************************************************/
3125 static struct api_struct api_samr_cmds [] =
3127 { "SAMR_CLOSE_HND" , SAMR_CLOSE_HND , api_samr_close_hnd },
3128 { "SAMR_CONNECT" , SAMR_CONNECT , api_samr_connect },
3129 { "SAMR_CONNECT_ANON" , SAMR_CONNECT_ANON , api_samr_connect_anon },
3130 { "SAMR_ENUM_DOMAINS" , SAMR_ENUM_DOMAINS , api_samr_enum_domains },
3131 { "SAMR_ENUM_DOM_USERS" , SAMR_ENUM_DOM_USERS , api_samr_enum_dom_users },
3132 { "SAMR_ENUM_DOM_GROUPS" , SAMR_ENUM_DOM_GROUPS , api_samr_enum_dom_groups },
3133 { "SAMR_ENUM_DOM_ALIASES" , SAMR_ENUM_DOM_ALIASES , api_samr_enum_dom_aliases },
3134 { "SAMR_QUERY_USERALIASES", SAMR_QUERY_USERALIASES, api_samr_query_useraliases},
3135 { "SAMR_QUERY_ALIASMEM" , SAMR_QUERY_ALIASMEM , api_samr_query_aliasmem },
3136 { "SAMR_QUERY_GROUPMEM" , SAMR_QUERY_GROUPMEM , api_samr_query_groupmem },
3137 { "SAMR_ADD_ALIASMEM" , SAMR_ADD_ALIASMEM , api_samr_add_aliasmem },
3138 { "SAMR_DEL_ALIASMEM" , SAMR_DEL_ALIASMEM , api_samr_del_aliasmem },
3139 { "SAMR_ADD_GROUPMEM" , SAMR_ADD_GROUPMEM , api_samr_add_groupmem },
3140 { "SAMR_DEL_GROUPMEM" , SAMR_DEL_GROUPMEM , api_samr_del_groupmem },
3141 { "SAMR_DELETE_DOM_GROUP" , SAMR_DELETE_DOM_GROUP , api_samr_delete_dom_group },
3142 { "SAMR_DELETE_DOM_ALIAS" , SAMR_DELETE_DOM_ALIAS , api_samr_delete_dom_alias },
3143 { "SAMR_CREATE_DOM_GROUP" , SAMR_CREATE_DOM_GROUP , api_samr_create_dom_group },
3144 { "SAMR_CREATE_DOM_ALIAS" , SAMR_CREATE_DOM_ALIAS , api_samr_create_dom_alias },
3145 { "SAMR_LOOKUP_NAMES" , SAMR_LOOKUP_NAMES , api_samr_lookup_names },
3146 { "SAMR_OPEN_USER" , SAMR_OPEN_USER , api_samr_open_user },
3147 { "SAMR_QUERY_USERINFO" , SAMR_QUERY_USERINFO , api_samr_query_userinfo },
3148 { "SAMR_SET_USERINFO" , SAMR_SET_USERINFO , api_samr_set_userinfo },
3149 { "SAMR_SET_USERINFO2" , SAMR_SET_USERINFO2 , api_samr_set_userinfo2 },
3150 { "SAMR_QUERY_DOMAIN_INFO", SAMR_QUERY_DOMAIN_INFO, api_samr_query_dom_info },
3151 { "SAMR_QUERY_USERGROUPS" , SAMR_QUERY_USERGROUPS , api_samr_query_usergroups },
3152 { "SAMR_QUERY_DISPINFO" , SAMR_QUERY_DISPINFO , api_samr_query_dispinfo },
3153 { "SAMR_QUERY_DISPINFO3" , SAMR_QUERY_DISPINFO3 , api_samr_query_dispinfo },
3154 { "SAMR_QUERY_DISPINFO4" , SAMR_QUERY_DISPINFO4 , api_samr_query_dispinfo },
3155 { "SAMR_QUERY_ALIASINFO" , SAMR_QUERY_ALIASINFO , api_samr_query_aliasinfo },
3156 { "SAMR_QUERY_GROUPINFO" , SAMR_QUERY_GROUPINFO , api_samr_query_groupinfo },
3157 { "SAMR_CREATE_USER" , SAMR_CREATE_USER , api_samr_create_user },
3158 { "SAMR_LOOKUP_RIDS" , SAMR_LOOKUP_RIDS , api_samr_lookup_rids },
3159 { "SAMR_GET_DOM_PWINFO" , SAMR_GET_DOM_PWINFO , api_samr_unknown_38 },
3160 { "SAMR_CHGPASSWD_USER" , SAMR_CHGPASSWD_USER , api_samr_chgpasswd_user },
3161 { "SAMR_OPEN_ALIAS" , SAMR_OPEN_ALIAS , api_samr_open_alias },
3162 { "SAMR_OPEN_GROUP" , SAMR_OPEN_GROUP , api_samr_open_group },
3163 { "SAMR_OPEN_DOMAIN" , SAMR_OPEN_DOMAIN , api_samr_open_domain },
3164 { "SAMR_LOOKUP_DOMAIN" , SAMR_LOOKUP_DOMAIN , api_samr_lookup_domain },
3165 { "SAMR_QUERY_SEC_OBJECT" , SAMR_QUERY_SEC_OBJECT , api_samr_unknown_3 },
3166 { "SAMR_GET_USRDOM_PWINFO", SAMR_GET_USRDOM_PWINFO, api_samr_unknown_2c },
3170 /*******************************************************************
3171 receives a samr pipe and responds.
3172 ********************************************************************/
3173 BOOL api_samr_rpc(pipes_struct *p, prs_struct *data)
3175 return api_rpcTNP(p, "api_samr_rpc", api_samr_cmds, data);