Win9x user level security.
[samba.git] / source3 / rpcclient / cmd_samr.c
1 /* 
2    Unix SMB/Netbios implementation.
3    Version 1.9.
4    NT Domain Authentication SMB / MSRPC client
5    Copyright (C) Andrew Tridgell 1994-1997
6    Copyright (C) Luke Kenneth Casson Leighton 1996-1997
7    
8    This program is free software; you can redistribute it and/or modify
9    it under the terms of the GNU General Public License as published by
10    the Free Software Foundation; either version 2 of the License, or
11    (at your option) any later version.
12    
13    This program is distributed in the hope that it will be useful,
14    but WITHOUT ANY WARRANTY; without even the implied warranty of
15    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16    GNU General Public License for more details.
17    
18    You should have received a copy of the GNU General Public License
19    along with this program; if not, write to the Free Software
20    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
21 */
22
23
24
25 #ifdef SYSLOG
26 #undef SYSLOG
27 #endif
28
29 #include "includes.h"
30 #include "nterr.h"
31
32 extern int DEBUGLEVEL;
33
34 #define DEBUG_TESTING
35
36 extern struct cli_state *smb_cli;
37
38 extern FILE* out_hnd;
39
40
41 /****************************************************************************
42 SAM password change
43 ****************************************************************************/
44 void cmd_sam_ntchange_pwd(struct client_info *info)
45 {
46         uint16 fnum;
47         fstring srv_name;
48         fstring domain;
49         fstring sid;
50         char *new_passwd;
51         BOOL res = True;
52         char nt_newpass[516];
53         uchar nt_hshhash[16];
54         uchar nt_newhash[16];
55         uchar nt_oldhash[16];
56         char lm_newpass[516];
57         uchar lm_newhash[16];
58         uchar lm_hshhash[16];
59         uchar lm_oldhash[16];
60
61         sid_to_string(sid, &info->dom.level5_sid);
62         fstrcpy(domain, info->dom.level5_dom);
63
64         fstrcpy(srv_name, "\\\\");
65         fstrcat(srv_name, info->dest_host);
66         strupper(srv_name);
67
68         fprintf(out_hnd, "SAM NT Password Change\n");
69
70 #if 0
71         struct pwd_info new_pwd;
72         pwd_read(&new_pwd, "New Password (ONCE: this is test code!):", True);
73 #endif
74         new_passwd = (char*)getpass("New Password (ONCE ONLY - get it right :-)");
75
76         nt_lm_owf_gen(new_passwd, lm_newhash, nt_newhash);
77         pwd_get_lm_nt_16(&(smb_cli->pwd), lm_oldhash, nt_oldhash );
78         make_oem_passwd_hash(nt_newpass, new_passwd, nt_oldhash, True);
79         make_oem_passwd_hash(lm_newpass, new_passwd, lm_oldhash, True);
80         E_old_pw_hash(lm_newhash, lm_oldhash, lm_hshhash);
81         E_old_pw_hash(lm_newhash, nt_oldhash, nt_hshhash);
82
83         cli_nt_set_ntlmssp_flgs(smb_cli,
84                                     NTLMSSP_NEGOTIATE_UNICODE |
85                                     NTLMSSP_NEGOTIATE_OEM |
86                                     NTLMSSP_NEGOTIATE_SIGN |
87                                     NTLMSSP_NEGOTIATE_SEAL |
88                                     NTLMSSP_NEGOTIATE_LM_KEY |
89                                     NTLMSSP_NEGOTIATE_NTLM |
90                                     NTLMSSP_NEGOTIATE_ALWAYS_SIGN |
91                                     NTLMSSP_NEGOTIATE_00001000 |
92                                     NTLMSSP_NEGOTIATE_00002000);
93
94         /* open SAMR session.  */
95         res = res ? cli_nt_session_open(smb_cli, PIPE_SAMR, &fnum) : False;
96
97         /* establish a connection. */
98         res = res ? samr_unknown_38(smb_cli, fnum, srv_name) : False;
99
100         /* establish a connection. */
101         res = res ? samr_chgpasswd_user(smb_cli, fnum,
102                                            srv_name, smb_cli->user_name,
103                                            nt_newpass, nt_hshhash,
104                                            lm_newpass, lm_hshhash) : False;
105         /* close the session */
106         cli_nt_session_close(smb_cli, fnum);
107
108         if (res)
109         {
110                 fprintf(out_hnd, "NT Password changed OK\n");
111         }
112         else
113         {
114                 fprintf(out_hnd, "NT Password change FAILED\n");
115         }
116 }
117
118
119 /****************************************************************************
120 experimental SAM encryted rpc test connection
121 ****************************************************************************/
122 void cmd_sam_test(struct client_info *info)
123 {
124         uint16 fnum;
125         fstring srv_name;
126         fstring domain;
127         fstring sid;
128         BOOL res = True;
129
130         sid_to_string(sid, &info->dom.level5_sid);
131         fstrcpy(domain, info->dom.level5_dom);
132
133 /*
134         if (strlen(sid) == 0)
135         {
136                 fprintf(out_hnd, "please use 'lsaquery' first, to ascertain the SID\n");
137                 return;
138         }
139 */
140         fstrcpy(srv_name, "\\\\");
141         fstrcat(srv_name, info->dest_host);
142         strupper(srv_name);
143
144         fprintf(out_hnd, "SAM Encryption Test\n");
145
146         cli_nt_set_ntlmssp_flgs(smb_cli,
147                                     NTLMSSP_NEGOTIATE_UNICODE |
148                                     NTLMSSP_NEGOTIATE_OEM |
149                                     NTLMSSP_NEGOTIATE_SIGN |
150                                     NTLMSSP_NEGOTIATE_SEAL |
151                                     NTLMSSP_NEGOTIATE_LM_KEY |
152                                     NTLMSSP_NEGOTIATE_NTLM |
153                                     NTLMSSP_NEGOTIATE_ALWAYS_SIGN |
154                                     NTLMSSP_NEGOTIATE_00001000 |
155                                     NTLMSSP_NEGOTIATE_00002000);
156
157         /* open SAMR session.  */
158         res = res ? cli_nt_session_open(smb_cli, PIPE_SAMR, &fnum) : False;
159
160         /* establish a connection. */
161         res = res ? samr_unknown_38(smb_cli, fnum, srv_name) : False;
162
163         /* close the session */
164         cli_nt_session_close(smb_cli, fnum);
165
166         if (res)
167         {
168                 DEBUG(5,("cmd_sam_test: succeeded\n"));
169         }
170         else
171         {
172                 DEBUG(5,("cmd_sam_test: failed\n"));
173         }
174 }
175
176 /****************************************************************************
177 Lookup domain in SAM server.
178 ****************************************************************************/
179 void cmd_sam_lookup_domain(struct client_info *info)
180 {
181         uint16 fnum;
182         fstring srv_name;
183         fstring domain;
184         fstring str_sid;
185         DOM_SID dom_sid;
186         BOOL res = True;
187
188         fstrcpy(srv_name, "\\\\");
189         fstrcat(srv_name, info->dest_host);
190         strupper(srv_name);
191
192         if (!next_token(NULL, domain, NULL, sizeof(domain)))
193         {
194                 fprintf(out_hnd, "lookupdomain: <name>\n");
195                 return;
196         }
197
198         fprintf(out_hnd, "Lookup Domain in SAM Server\n");
199
200         /* open SAMR session.  negotiate credentials */
201         res = res ? cli_nt_session_open(smb_cli, PIPE_SAMR, &fnum) : False;
202
203         /* establish a connection. */
204         res = res ? samr_connect(smb_cli, fnum, 
205                                 srv_name, 0x00000020,
206                                 &info->dom.samr_pol_connect) : False;
207
208         /* connect to the domain */
209         res = res ? samr_query_lookup_domain(smb_cli, fnum, 
210                     &info->dom.samr_pol_connect, domain, &dom_sid) : False;
211
212         res = res ? samr_close(smb_cli, fnum, &info->dom.samr_pol_connect) : False;
213
214         /* close the session */
215         cli_nt_session_close(smb_cli, fnum);
216
217         if (res)
218         {
219                 DEBUG(5,("cmd_sam_lookup_domain: succeeded\n"));
220
221                 sid_to_string(str_sid, &dom_sid);
222                 fprintf(out_hnd, "%s SID: %s\n", domain, str_sid);
223                 fprintf(out_hnd, "Lookup Domain: OK\n");
224         }
225         else
226         {
227                 DEBUG(5,("cmd_sam_lookup_domain: failed\n"));
228                 fprintf(out_hnd, "Lookup Domain: FAILED\n");
229         }
230 }
231
232 /****************************************************************************
233 SAM delete alias member.
234 ****************************************************************************/
235 void cmd_sam_del_aliasmem(struct client_info *info)
236 {
237         uint16 fnum;
238         fstring srv_name;
239         fstring domain;
240         fstring tmp;
241         fstring sid;
242         DOM_SID sid1;
243         POLICY_HND alias_pol;
244         BOOL res = True;
245         BOOL res1 = True;
246         BOOL res2 = True;
247         uint32 flags = 0x200003f3; /* absolutely no idea. */
248         DOM_SID member_sid; 
249         uint32 alias_rid;
250
251         sid_copy(&sid1, &info->dom.level5_sid);
252         sid_to_string(sid, &sid1);
253         fstrcpy(domain, info->dom.level5_dom);
254
255         if (sid1.num_auths == 0)
256         {
257                 fprintf(out_hnd, "please use 'lsaquery' first, to ascertain the SID\n");
258                 return;
259         }
260
261         fstrcpy(srv_name, "\\\\");
262         fstrcat(srv_name, info->dest_host);
263         strupper(srv_name);
264
265         if (!next_token(NULL, tmp, NULL, sizeof(tmp)))
266         {
267                 fprintf(out_hnd, "delaliasmem: <alias rid> [member sid1] [member sid2] ...\n");
268                 return;
269         }
270         alias_rid = get_number(tmp);
271
272         fprintf(out_hnd, "SAM Domain Alias Member\n");
273
274         /* open SAMR session.  negotiate credentials */
275         res = res ? cli_nt_session_open(smb_cli, PIPE_SAMR, &fnum) : False;
276
277         /* establish a connection. */
278         res = res ? samr_connect(smb_cli, fnum, 
279                                 srv_name, 0x00000020,
280                                 &info->dom.samr_pol_connect) : False;
281
282         /* connect to the domain */
283         res = res ? samr_open_domain(smb_cli, fnum, 
284                     &info->dom.samr_pol_connect, flags, &sid1,
285                     &info->dom.samr_pol_open_domain) : False;
286
287         /* connect to the domain */
288         res1 = res ? samr_open_alias(smb_cli, fnum,
289                     &info->dom.samr_pol_open_domain,
290                     0x000f001f, alias_rid, &alias_pol) : False;
291
292         while (next_token(NULL, tmp, NULL, sizeof(tmp)) && res2 && res1)
293         {
294                 /* get a sid, delete a member from the alias */
295                 res2 = res2 ? string_to_sid(&member_sid, tmp) : False;
296                 res2 = res2 ? samr_del_aliasmem(smb_cli, fnum, &alias_pol, &member_sid) : False;
297
298                 if (res2)
299                 {
300                         fprintf(out_hnd, "SID deleted from Alias 0x%x: %s\n", alias_rid, tmp);
301                 }
302         }
303
304         res1 = res1 ? samr_close(smb_cli, fnum, &alias_pol) : False;
305         res  = res  ? samr_close(smb_cli, fnum, &info->dom.samr_pol_open_domain) : False;
306         res  = res  ? samr_close(smb_cli, fnum, &info->dom.samr_pol_connect) : False;
307
308         /* close the session */
309         cli_nt_session_close(smb_cli, fnum);
310
311         if (res && res1 && res2)
312         {
313                 DEBUG(5,("cmd_sam_del_aliasmem: succeeded\n"));
314                 fprintf(out_hnd, "Delete Domain Alias Member: OK\n");
315         }
316         else
317         {
318                 DEBUG(5,("cmd_sam_del_aliasmem: failed\n"));
319                 fprintf(out_hnd, "Delete Domain Alias Member: FAILED\n");
320         }
321 }
322
323 /****************************************************************************
324 SAM delete alias.
325 ****************************************************************************/
326 void cmd_sam_delete_dom_alias(struct client_info *info)
327 {
328         uint16 fnum;
329         fstring srv_name;
330         fstring domain;
331         fstring name;
332         fstring sid;
333         DOM_SID sid1;
334         POLICY_HND alias_pol;
335         BOOL res = True;
336         BOOL res1 = True;
337         BOOL res2 = True;
338         uint32 flags = 0x200003f3; /* absolutely no idea. */
339         uint32 alias_rid = 0;
340         const char *names[1];
341         uint32 rid [MAX_LOOKUP_SIDS];
342         uint32 type[MAX_LOOKUP_SIDS];
343         uint32 num_rids;
344
345         sid_copy(&sid1, &info->dom.level5_sid);
346         sid_to_string(sid, &sid1);
347         fstrcpy(domain, info->dom.level5_dom);
348
349         if (sid1.num_auths == 0)
350         {
351                 fprintf(out_hnd, "please use 'lsaquery' first, to ascertain the SID\n");
352                 return;
353         }
354
355         fstrcpy(srv_name, "\\\\");
356         fstrcat(srv_name, info->dest_host);
357         strupper(srv_name);
358
359         if (!next_token(NULL, name, NULL, sizeof(name)))
360         {
361                 fprintf(out_hnd, "delalias <alias name>\n");
362                 return;
363         }
364
365         fprintf(out_hnd, "SAM Delete Domain Alias\n");
366
367         /* open SAMR session.  negotiate credentials */
368         res = res ? cli_nt_session_open(smb_cli, PIPE_SAMR, &fnum) : False;
369
370         /* establish a connection. */
371         res = res ? samr_connect(smb_cli, fnum, 
372                                 srv_name, 0x00000020,
373                                 &info->dom.samr_pol_connect) : False;
374
375         /* connect to the domain */
376         res = res ? samr_open_domain(smb_cli, fnum, 
377                     &info->dom.samr_pol_connect, flags, &sid1,
378                     &info->dom.samr_pol_open_domain) : False;
379
380         names[0] = name;
381
382         res1 = res ? samr_query_lookup_names(smb_cli, fnum,
383                     &info->dom.samr_pol_open_domain, 0x000003e8,
384                     1, names,
385                     &num_rids, rid, type) : False;
386
387         if (res1 && num_rids == 1)
388         {
389                 alias_rid = rid[0];
390         }
391
392         /* connect to the domain */
393         res1 = res1 ? samr_open_alias(smb_cli, fnum,
394                     &info->dom.samr_pol_open_domain,
395                     0x000f001f, alias_rid, &alias_pol) : False;
396
397         res2 = res1 ? samr_delete_dom_alias(smb_cli, fnum, &alias_pol) : False;
398
399         res1 = res1 ? samr_close(smb_cli, fnum, &alias_pol) : False;
400         res  = res  ? samr_close(smb_cli, fnum, &info->dom.samr_pol_open_domain) : False;
401         res  = res  ? samr_close(smb_cli, fnum, &info->dom.samr_pol_connect) : False;
402
403         /* close the session */
404         cli_nt_session_close(smb_cli, fnum);
405
406         if (res && res1 && res2)
407         {
408                 DEBUG(5,("cmd_sam_delete_dom_alias: succeeded\n"));
409                 fprintf(out_hnd, "Delete Domain Alias: OK\n");
410         }
411         else
412         {
413                 DEBUG(5,("cmd_sam_delete_dom_alias: failed\n"));
414                 fprintf(out_hnd, "Delete Domain Alias: FAILED\n");
415         }
416 }
417
418 /****************************************************************************
419 SAM add alias member.
420 ****************************************************************************/
421 void cmd_sam_add_aliasmem(struct client_info *info)
422 {
423         uint16 fnum;
424         uint16 fnum_lsa;
425         fstring srv_name;
426         fstring domain;
427         fstring tmp;
428         fstring sid;
429         DOM_SID sid1;
430         POLICY_HND alias_pol;
431         BOOL res = True;
432         BOOL res1 = True;
433         BOOL res2 = True;
434         BOOL res3 = True;
435         BOOL res4 = True;
436         uint32 flags = 0x200003f3; /* absolutely no idea. */
437         uint32 alias_rid;
438         const char **names = NULL;
439         int num_names = 0;
440         DOM_SID *sids = NULL; 
441         int num_sids = 0;
442         int i;
443
444         sid_copy(&sid1, &info->dom.level5_sid);
445         sid_to_string(sid, &sid1);
446         fstrcpy(domain, info->dom.level5_dom);
447
448         if (sid1.num_auths == 0)
449         {
450                 fprintf(out_hnd, "please use 'lsaquery' first, to ascertain the SID\n");
451                 return;
452         }
453
454         fstrcpy(srv_name, "\\\\");
455         fstrcat(srv_name, info->dest_host);
456         strupper(srv_name);
457
458         while (next_token(NULL, tmp, NULL, sizeof(tmp)))
459         {
460                 num_names++;
461                 names = Realloc(names, num_names * sizeof(char*));
462                 if (names == NULL)
463                 {
464                         DEBUG(0,("Realloc returned NULL\n"));
465                         return;
466                 }
467                 names[num_names-1] = strdup(tmp);
468         }
469
470         if (num_names < 2)
471         {
472                 fprintf(out_hnd, "addaliasmem <group name> [member name1] [member name2] ...\n");
473                 return;
474         }
475         
476         fprintf(out_hnd, "SAM Domain Alias Member\n");
477
478         /* open LSARPC session. */
479         res3 = res3 ? cli_nt_session_open(smb_cli, PIPE_LSARPC, &fnum_lsa) : False;
480
481         /* lookup domain controller; receive a policy handle */
482         res3 = res3 ? lsa_open_policy(smb_cli, fnum_lsa,
483                                 srv_name,
484                                 &info->dom.lsa_info_pol, True) : False;
485
486         /* send lsa lookup sids call */
487         res4 = res3 ? lsa_lookup_names(smb_cli, fnum_lsa, 
488                                        &info->dom.lsa_info_pol,
489                                        num_names, names, 
490                                        &sids, NULL, &num_sids) : False;
491
492         res3 = res3 ? lsa_close(smb_cli, fnum_lsa, &info->dom.lsa_info_pol) : False;
493
494         cli_nt_session_close(smb_cli, fnum_lsa);
495
496         res4 = num_sids < 2 ? False : res4;
497
498         if (res4)
499         {
500                 /*
501                  * accept domain sid or builtin sid
502                  */
503
504                 DOM_SID sid_1_5_20;
505                 string_to_sid(&sid_1_5_20, "S-1-5-32");
506                 sid_split_rid(&sids[0], &alias_rid);
507
508                 if (sid_equal(&sids[0], &sid_1_5_20))
509                 {
510                         sid_copy(&sid1, &sid_1_5_20);
511                 }
512                 else if (!sid_equal(&sids[0], &sid1))
513                 {       
514                         res4 = False;
515                 }
516         }
517
518         /* open SAMR session.  negotiate credentials */
519         res = res4 ? cli_nt_session_open(smb_cli, PIPE_SAMR, &fnum) : False;
520
521         /* establish a connection. */
522         res = res ? samr_connect(smb_cli, fnum, 
523                                 srv_name, 0x00000020,
524                                 &info->dom.samr_pol_connect) : False;
525
526         /* connect to the domain */
527         res = res ? samr_open_domain(smb_cli, fnum, 
528                     &info->dom.samr_pol_connect, flags, &sid1,
529                     &info->dom.samr_pol_open_domain) : False;
530
531         /* connect to the domain */
532         res1 = res ? samr_open_alias(smb_cli, fnum,
533                     &info->dom.samr_pol_open_domain,
534                     0x000f001f, alias_rid, &alias_pol) : False;
535
536         for (i = 1; i < num_sids && res2 && res1; i++)
537         {
538                 /* add a member to the alias */
539                 res2 = res2 ? samr_add_aliasmem(smb_cli, fnum, &alias_pol, &sids[i]) : False;
540
541                 if (res2)
542                 {
543                         sid_to_string(tmp, &sids[i]);
544                         fprintf(out_hnd, "SID added to Alias 0x%x: %s\n", alias_rid, tmp);
545                 }
546         }
547
548         res1 = res1 ? samr_close(smb_cli, fnum, &alias_pol) : False;
549         res  = res  ? samr_close(smb_cli, fnum, &info->dom.samr_pol_open_domain) : False;
550         res  = res  ? samr_close(smb_cli, fnum, &info->dom.samr_pol_connect) : False;
551
552         /* close the session */
553         cli_nt_session_close(smb_cli, fnum);
554
555         if (sids != NULL)
556         {
557                 free(sids);
558         }
559         
560         if (names != NULL)
561         {
562                 for (i = 0; i < num_names; i++)
563                 {
564                         if (names[i] != NULL)
565                         {
566                                 free(((char**)(names))[i]);
567                         }
568                 }
569                 free(names);
570         }
571         
572         if (res && res1 && res2)
573         {
574                 DEBUG(5,("cmd_sam_add_aliasmem: succeeded\n"));
575                 fprintf(out_hnd, "Add Domain Alias Member: OK\n");
576         }
577         else
578         {
579                 DEBUG(5,("cmd_sam_add_aliasmem: failed\n"));
580                 fprintf(out_hnd, "Add Domain Alias Member: FAILED\n");
581         }
582 }
583
584
585 /****************************************************************************
586 SAM create domain alias.
587 ****************************************************************************/
588 void cmd_sam_create_dom_alias(struct client_info *info)
589 {
590         uint16 fnum;
591         fstring srv_name;
592         fstring domain;
593         fstring acct_name;
594         fstring acct_desc;
595         fstring sid;
596         DOM_SID sid1;
597         BOOL res = True;
598         BOOL res1 = True;
599         uint32 flags = 0x200003f3; /* absolutely no idea. */
600         uint32 alias_rid; 
601
602         sid_copy(&sid1, &info->dom.level5_sid);
603         sid_to_string(sid, &sid1);
604         fstrcpy(domain, info->dom.level5_dom);
605
606         if (sid1.num_auths == 0)
607         {
608                 fprintf(out_hnd, "please use 'lsaquery' first, to ascertain the SID\n");
609                 return;
610         }
611
612
613         fstrcpy(srv_name, "\\\\");
614         fstrcat(srv_name, info->dest_host);
615         strupper(srv_name);
616
617         if (!next_token(NULL, acct_name, NULL, sizeof(acct_name)))
618         {
619                 fprintf(out_hnd, "createalias: <acct name> [acct description]\n");
620         }
621
622         if (!next_token(NULL, acct_desc, NULL, sizeof(acct_desc)))
623         {
624                 acct_desc[0] = 0;
625         }
626
627
628         fprintf(out_hnd, "SAM Create Domain Alias\n");
629         fprintf(out_hnd, "Domain: %s Name: %s Description: %s\n",
630                           domain, acct_name, acct_desc);
631
632         /* open SAMR session.  negotiate credentials */
633         res = res ? cli_nt_session_open(smb_cli, PIPE_SAMR, &fnum) : False;
634
635         /* establish a connection. */
636         res = res ? samr_connect(smb_cli, fnum, 
637                                 srv_name, 0x00000020,
638                                 &info->dom.samr_pol_connect) : False;
639
640         /* connect to the domain */
641         res = res ? samr_open_domain(smb_cli, fnum, 
642                     &info->dom.samr_pol_connect, flags, &sid1,
643                     &info->dom.samr_pol_open_domain) : False;
644
645         /* create a domain alias */
646         res1 = res ? create_samr_domain_alias(smb_cli, fnum, 
647                                 &info->dom.samr_pol_open_domain,
648                                 acct_name, acct_desc, &alias_rid) : False;
649
650         res = res ? samr_close(smb_cli, fnum,
651                     &info->dom.samr_pol_open_domain) : False;
652
653         res = res ? samr_close(smb_cli, fnum,
654                     &info->dom.samr_pol_connect) : False;
655
656         /* close the session */
657         cli_nt_session_close(smb_cli, fnum);
658
659         if (res && res1)
660         {
661                 DEBUG(5,("cmd_sam_create_dom_alias: succeeded\n"));
662                 fprintf(out_hnd, "Create Domain Alias: OK\n");
663         }
664         else
665         {
666                 DEBUG(5,("cmd_sam_create_dom_alias: failed\n"));
667                 fprintf(out_hnd, "Create Domain Alias: FAILED\n");
668         }
669 }
670
671
672 /****************************************************************************
673 SAM delete group member.
674 ****************************************************************************/
675 void cmd_sam_del_groupmem(struct client_info *info)
676 {
677         uint16 fnum;
678         fstring srv_name;
679         fstring domain;
680         fstring tmp;
681         fstring sid;
682         DOM_SID sid1;
683         POLICY_HND group_pol;
684         BOOL res = True;
685         BOOL res1 = True;
686         BOOL res2 = True;
687         uint32 flags = 0x200003f3; /* absolutely no idea. */
688         uint32 member_rid; 
689         uint32 group_rid;
690
691         sid_copy(&sid1, &info->dom.level5_sid);
692         sid_to_string(sid, &sid1);
693         fstrcpy(domain, info->dom.level5_dom);
694
695         if (sid1.num_auths == 0)
696         {
697                 fprintf(out_hnd, "please use 'lsaquery' first, to ascertain the SID\n");
698                 return;
699         }
700
701         fstrcpy(srv_name, "\\\\");
702         fstrcat(srv_name, info->dest_host);
703         strupper(srv_name);
704
705         if (!next_token(NULL, tmp, NULL, sizeof(tmp)))
706         {
707                 fprintf(out_hnd, "delgroupmem: <group rid> [member rid1] [member rid2] ...\n");
708                 return;
709         }
710         group_rid = get_number(tmp);
711
712         fprintf(out_hnd, "SAM Add Domain Group member\n");
713
714         /* open SAMR session.  negotiate credentials */
715         res = res ? cli_nt_session_open(smb_cli, PIPE_SAMR, &fnum) : False;
716
717         /* establish a connection. */
718         res = res ? samr_connect(smb_cli, fnum, 
719                                 srv_name, 0x00000020,
720                                 &info->dom.samr_pol_connect) : False;
721
722         /* connect to the domain */
723         res = res ? samr_open_domain(smb_cli, fnum, 
724                     &info->dom.samr_pol_connect, flags, &sid1,
725                     &info->dom.samr_pol_open_domain) : False;
726
727         /* connect to the domain */
728         res1 = res ? samr_open_group(smb_cli, fnum,
729                     &info->dom.samr_pol_open_domain,
730                     0x0000001f, group_rid, &group_pol) : False;
731
732         while (next_token(NULL, tmp, NULL, sizeof(tmp)) && res2 && res1)
733         {
734                 /* get a rid, delete a member from the group */
735                 member_rid = get_number(tmp);
736                 res2 = res2 ? samr_del_groupmem(smb_cli, fnum, &group_pol, member_rid) : False;
737
738                 if (res2)
739                 {
740                         fprintf(out_hnd, "RID deleted from Group 0x%x: 0x%x\n", group_rid, member_rid);
741                 }
742         }
743
744         res1 = res1 ? samr_close(smb_cli, fnum, &group_pol) : False;
745         res  = res  ? samr_close(smb_cli, fnum, &info->dom.samr_pol_open_domain) : False;
746         res  = res  ? samr_close(smb_cli, fnum, &info->dom.samr_pol_connect) : False;
747
748         /* close the session */
749         cli_nt_session_close(smb_cli, fnum);
750
751         if (res && res1 && res2)
752         {
753                 DEBUG(5,("cmd_sam_del_groupmem: succeeded\n"));
754                 fprintf(out_hnd, "Add Domain Group Member: OK\n");
755         }
756         else
757         {
758                 DEBUG(5,("cmd_sam_del_groupmem: failed\n"));
759                 fprintf(out_hnd, "Add Domain Group Member: FAILED\n");
760         }
761 }
762
763
764 /****************************************************************************
765 SAM delete group.
766 ****************************************************************************/
767 void cmd_sam_delete_dom_group(struct client_info *info)
768 {
769         uint16 fnum;
770         fstring srv_name;
771         fstring domain;
772         fstring name;
773         fstring sid;
774         DOM_SID sid1;
775         POLICY_HND group_pol;
776         BOOL res = True;
777         BOOL res1 = True;
778         BOOL res2 = True;
779         uint32 flags = 0x200003f3; /* absolutely no idea. */
780         uint32 group_rid = 0;
781         const char *names[1];
782         uint32 rid [MAX_LOOKUP_SIDS];
783         uint32 type[MAX_LOOKUP_SIDS];
784         uint32 num_rids;
785
786         sid_copy(&sid1, &info->dom.level5_sid);
787         sid_to_string(sid, &sid1);
788         fstrcpy(domain, info->dom.level5_dom);
789
790         if (sid1.num_auths == 0)
791         {
792                 fprintf(out_hnd, "please use 'lsaquery' first, to ascertain the SID\n");
793                 return;
794         }
795
796         fstrcpy(srv_name, "\\\\");
797         fstrcat(srv_name, info->dest_host);
798         strupper(srv_name);
799
800         if (!next_token(NULL, name, NULL, sizeof(name)))
801         {
802                 fprintf(out_hnd, "delgroup <group name>\n");
803                 return;
804         }
805
806         fprintf(out_hnd, "SAM Delete Domain Group\n");
807
808         /* open SAMR session.  negotiate credentials */
809         res = res ? cli_nt_session_open(smb_cli, PIPE_SAMR, &fnum) : False;
810
811         /* establish a connection. */
812         res = res ? samr_connect(smb_cli, fnum, 
813                                 srv_name, 0x00000020,
814                                 &info->dom.samr_pol_connect) : False;
815
816         /* connect to the domain */
817         res = res ? samr_open_domain(smb_cli, fnum, 
818                     &info->dom.samr_pol_connect, flags, &sid1,
819                     &info->dom.samr_pol_open_domain) : False;
820
821         names[0] = name;
822
823         res1 = res ? samr_query_lookup_names(smb_cli, fnum,
824                     &info->dom.samr_pol_open_domain, 0x000003e8,
825                     1, names,
826                     &num_rids, rid, type) : False;
827
828         if (res1 && num_rids == 1)
829         {
830                 group_rid = rid[0];
831         }
832
833         /* connect to the domain */
834         res1 = res1 ? samr_open_group(smb_cli, fnum,
835                     &info->dom.samr_pol_open_domain,
836                     0x0000001f, group_rid, &group_pol) : False;
837
838         res2 = res1 ? samr_delete_dom_group(smb_cli, fnum, &group_pol) : False;
839
840         res1 = res1 ? samr_close(smb_cli, fnum, &group_pol) : False;
841         res  = res  ? samr_close(smb_cli, fnum, &info->dom.samr_pol_open_domain) : False;
842         res  = res  ? samr_close(smb_cli, fnum, &info->dom.samr_pol_connect) : False;
843
844         /* close the session */
845         cli_nt_session_close(smb_cli, fnum);
846
847         if (res && res1 && res2)
848         {
849                 DEBUG(5,("cmd_sam_delete_dom_group: succeeded\n"));
850                 fprintf(out_hnd, "Delete Domain Group: OK\n");
851         }
852         else
853         {
854                 DEBUG(5,("cmd_sam_delete_dom_group: failed\n"));
855                 fprintf(out_hnd, "Delete Domain Group: FAILED\n");
856         }
857 }
858
859
860 /****************************************************************************
861 SAM add group member.
862 ****************************************************************************/
863 void cmd_sam_add_groupmem(struct client_info *info)
864 {
865         uint16 fnum;
866         fstring srv_name;
867         fstring domain;
868         fstring tmp;
869         fstring sid;
870         DOM_SID sid1;
871         POLICY_HND group_pol;
872         BOOL res = True;
873         BOOL res1 = True;
874         BOOL res2 = True;
875         uint32 flags = 0x200003f3; /* absolutely no idea. */
876         uint32 group_rid = 0;
877         const char **names = NULL;
878         uint32 num_names = 0;
879         uint32 rid [MAX_LOOKUP_SIDS];
880         uint32 type[MAX_LOOKUP_SIDS];
881         uint32 num_rids;
882         int i;
883
884         sid_copy(&sid1, &info->dom.level5_sid);
885         sid_to_string(sid, &sid1);
886         fstrcpy(domain, info->dom.level5_dom);
887
888         if (sid1.num_auths == 0)
889         {
890                 fprintf(out_hnd, "please use 'lsaquery' first, to ascertain the SID\n");
891                 return;
892         }
893
894         fstrcpy(srv_name, "\\\\");
895         fstrcat(srv_name, info->dest_host);
896         strupper(srv_name);
897
898         while (next_token(NULL, tmp, NULL, sizeof(tmp)))
899         {
900                 num_names++;
901                 names = Realloc(names, num_names * sizeof(char*));
902                 if (names == NULL)
903                 {
904                         DEBUG(0,("Realloc returned NULL\n"));
905                         return;
906                 }
907                 names[num_names-1] = strdup(tmp);
908         }
909
910         if (num_names < 2)
911         {
912                 fprintf(out_hnd, "addgroupmem <group name> [member name1] [member name2] ...\n");
913                 return;
914         }
915         
916         fprintf(out_hnd, "SAM Add Domain Group member\n");
917
918         /* open SAMR session.  negotiate credentials */
919         res = res ? cli_nt_session_open(smb_cli, PIPE_SAMR, &fnum) : False;
920
921         /* establish a connection. */
922         res = res ? samr_connect(smb_cli, fnum, 
923                                 srv_name, 0x00000020,
924                                 &info->dom.samr_pol_connect) : False;
925
926         /* connect to the domain */
927         res = res ? samr_open_domain(smb_cli, fnum, 
928                     &info->dom.samr_pol_connect, flags, &sid1,
929                     &info->dom.samr_pol_open_domain) : False;
930
931         res1 = res ? samr_query_lookup_names(smb_cli, fnum,
932                     &info->dom.samr_pol_open_domain, 0x000003e8,
933                     num_names, names,
934                     &num_rids, rid, type) : False;
935
936         if (res1 && num_rids != 0)
937         {
938                 group_rid = rid[0];
939         }
940
941         /* connect to the domain */
942         res1 = res1 ? samr_open_group(smb_cli, fnum,
943                     &info->dom.samr_pol_open_domain,
944                     0x0000001f, group_rid, &group_pol) : False;
945
946         for (i = 1; i < num_rids && res2 && res1; i++)
947         {
948                 res2 = res2 ? samr_add_groupmem(smb_cli, fnum, &group_pol, rid[i]) : False;
949
950                 if (res2)
951                 {
952                         fprintf(out_hnd, "RID added to Group 0x%x: 0x%x\n", group_rid, rid[i]);
953                 }
954         }
955
956         res1 = res1 ? samr_close(smb_cli, fnum, &group_pol) : False;
957         res  = res  ? samr_close(smb_cli, fnum, &info->dom.samr_pol_open_domain) : False;
958         res  = res  ? samr_close(smb_cli, fnum, &info->dom.samr_pol_connect) : False;
959
960         /* close the session */
961         cli_nt_session_close(smb_cli, fnum);
962
963         if (names != NULL)
964         {
965                 for (i = 0; i < num_names; i++)
966                 {
967                         if (names[i] != NULL)
968                         {
969                                 free(((char**)(names))[i]);
970                         }
971                 }
972                 free(names);
973         }
974         
975         if (res && res1 && res2)
976         {
977                 DEBUG(5,("cmd_sam_add_groupmem: succeeded\n"));
978                 fprintf(out_hnd, "Add Domain Group Member: OK\n");
979         }
980         else
981         {
982                 DEBUG(5,("cmd_sam_add_groupmem: failed\n"));
983                 fprintf(out_hnd, "Add Domain Group Member: FAILED\n");
984         }
985 }
986
987
988 /****************************************************************************
989 SAM create domain group.
990 ****************************************************************************/
991 void cmd_sam_create_dom_group(struct client_info *info)
992 {
993         uint16 fnum;
994         fstring srv_name;
995         fstring domain;
996         fstring acct_name;
997         fstring acct_desc;
998         fstring sid;
999         DOM_SID sid1;
1000         BOOL res = True;
1001         BOOL res1 = True;
1002         uint32 flags = 0x220; /* absolutely no idea. */
1003         uint32 group_rid; 
1004
1005         sid_copy(&sid1, &info->dom.level5_sid);
1006         sid_to_string(sid, &sid1);
1007         fstrcpy(domain, info->dom.level5_dom);
1008
1009         if (sid1.num_auths == 0)
1010         {
1011                 fprintf(out_hnd, "please use 'lsaquery' first, to ascertain the SID\n");
1012                 return;
1013         }
1014
1015
1016         fstrcpy(srv_name, "\\\\");
1017         fstrcat(srv_name, info->dest_host);
1018         strupper(srv_name);
1019
1020         if (!next_token(NULL, acct_name, NULL, sizeof(acct_name)))
1021         {
1022                 fprintf(out_hnd, "creategroup: <acct name> [acct description]\n");
1023         }
1024
1025         if (!next_token(NULL, acct_desc, NULL, sizeof(acct_desc)))
1026         {
1027                 acct_desc[0] = 0;
1028         }
1029
1030
1031         fprintf(out_hnd, "SAM Create Domain Group\n");
1032         fprintf(out_hnd, "Domain: %s Name: %s Description: %s\n",
1033                           domain, acct_name, acct_desc);
1034
1035         /* open SAMR session.  negotiate credentials */
1036         res = res ? cli_nt_session_open(smb_cli, PIPE_SAMR, &fnum) : False;
1037
1038         /* establish a connection. */
1039         res = res ? samr_connect(smb_cli, fnum, 
1040                                 srv_name, 0x00000020,
1041                                 &info->dom.samr_pol_connect) : False;
1042
1043         /* connect to the domain */
1044         res = res ? samr_open_domain(smb_cli, fnum, 
1045                     &info->dom.samr_pol_connect, flags, &sid1,
1046                     &info->dom.samr_pol_open_domain) : False;
1047
1048         /* read some users */
1049         res1 = res ? create_samr_domain_group(smb_cli, fnum, 
1050                                 &info->dom.samr_pol_open_domain,
1051                                 acct_name, acct_desc, &group_rid) : False;
1052
1053         res = res ? samr_close(smb_cli, fnum,
1054                     &info->dom.samr_pol_open_domain) : False;
1055
1056         res = res ? samr_close(smb_cli, fnum,
1057                     &info->dom.samr_pol_connect) : False;
1058
1059         /* close the session */
1060         cli_nt_session_close(smb_cli, fnum);
1061
1062         if (res && res1)
1063         {
1064                 DEBUG(5,("cmd_sam_create_dom_group: succeeded\n"));
1065                 fprintf(out_hnd, "Create Domain Group: OK\n");
1066         }
1067         else
1068         {
1069                 DEBUG(5,("cmd_sam_create_dom_group: failed\n"));
1070                 fprintf(out_hnd, "Create Domain Group: FAILED\n");
1071         }
1072 }
1073
1074
1075 /****************************************************************************
1076 experimental SAM users enum.
1077 ****************************************************************************/
1078 void cmd_sam_enum_users(struct client_info *info)
1079 {
1080         uint16 fnum;
1081         fstring srv_name;
1082         fstring domain;
1083         fstring sid;
1084         DOM_SID sid1;
1085         DOM_SID sid_1_5_20;
1086         int user_idx;
1087         BOOL res = True;
1088         BOOL res1 = True;
1089         BOOL request_user_info  = False;
1090         BOOL request_group_info = False;
1091         BOOL request_alias_info = False;
1092         uint16 start_idx = 0x0;
1093         uint16 unk_0 = 0x0;
1094         uint16 acb_mask = 0;
1095         uint16 unk_1 = 0x0;
1096         uint32 flags = 0x304; /* absolutely no idea. */
1097         fstring tmp;
1098         int i;
1099
1100         sid_copy(&sid1, &info->dom.level5_sid);
1101         sid_to_string(sid, &sid1);
1102         fstrcpy(domain, info->dom.level5_dom);
1103
1104         if (sid1.num_auths == 0)
1105         {
1106                 fprintf(out_hnd, "please use 'lsaquery' first, to ascertain the SID\n");
1107                 return;
1108         }
1109
1110
1111         fstrcpy(srv_name, "\\\\");
1112         fstrcat(srv_name, info->dest_host);
1113         strupper(srv_name);
1114
1115         for (i = 0; i < 3; i++)
1116         {
1117                 /* a bad way to do token parsing... */
1118                 if (next_token(NULL, tmp, NULL, sizeof(tmp)))
1119                 {
1120                         request_user_info  |= strequal(tmp, "-u");
1121                         request_group_info |= strequal(tmp, "-g");
1122                         request_alias_info |= strequal(tmp, "-a");
1123                 }
1124                 else
1125                 {
1126                         break;
1127                 }
1128         }
1129
1130 #ifdef DEBUG_TESTING
1131         if (next_token(NULL, tmp, NULL, sizeof(tmp)))
1132         {
1133                 start_idx = (uint32)strtol(tmp, (char**)NULL, 10);
1134         }
1135
1136         if (next_token(NULL, tmp, NULL, sizeof(tmp)))
1137         {
1138                 unk_0 = (uint16)strtol(tmp, (char**)NULL, 16);
1139         }
1140
1141         if (next_token(NULL, tmp, NULL, sizeof(tmp)))
1142         {
1143                 acb_mask = (uint16)strtol(tmp, (char**)NULL, 16);
1144         }
1145
1146         if (next_token(NULL, tmp, NULL, sizeof(tmp)))
1147         {
1148                 unk_1 = (uint16)strtol(tmp, (char**)NULL, 16);
1149         }
1150 #endif
1151
1152         string_to_sid(&sid_1_5_20, "S-1-5-32");
1153
1154         fprintf(out_hnd, "SAM Enumerate Users\n");
1155         fprintf(out_hnd, "From: %s To: %s Domain: %s SID: %s\n",
1156                           info->myhostname, srv_name, domain, sid);
1157
1158 #ifdef DEBUG_TESTING
1159         DEBUG(5,("Number of entries:%d unk_0:%04x acb_mask:%04x unk_1:%04x\n",
1160                   start_idx, unk_0, acb_mask, unk_1));
1161 #endif
1162
1163         /* open SAMR session.  negotiate credentials */
1164         res = res ? cli_nt_session_open(smb_cli, PIPE_SAMR, &fnum) : False;
1165
1166         /* establish a connection. */
1167         res = res ? samr_connect(smb_cli, fnum, 
1168                                 srv_name, 0x00000020,
1169                                 &info->dom.samr_pol_connect) : False;
1170
1171         /* connect to the domain */
1172         res = res ? samr_open_domain(smb_cli, fnum, 
1173                     &info->dom.samr_pol_connect, flags, &sid1,
1174                     &info->dom.samr_pol_open_domain) : False;
1175
1176         /* connect to the S-1-5-20 domain */
1177         res1 = res ? samr_open_domain(smb_cli, fnum, 
1178                     &info->dom.samr_pol_connect, flags, &sid_1_5_20,
1179                     &info->dom.samr_pol_open_builtindom) : False;
1180
1181         info->dom.sam = NULL;
1182
1183         /* read some users */
1184         res = res ? samr_enum_dom_users(smb_cli, fnum, 
1185                      &info->dom.samr_pol_open_domain,
1186                      start_idx, acb_mask, unk_1, 0x8000,
1187                      &info->dom.sam, &info->dom.num_sam_entries) : False;
1188
1189         if (res && info->dom.num_sam_entries == 0)
1190         {
1191                 fprintf(out_hnd, "No users\n");
1192         }
1193
1194                 /* query all the users */
1195         for (user_idx = 0; res && user_idx < info->dom.num_sam_entries; user_idx++)
1196                 {
1197                 uint32 user_rid = info->dom.sam[user_idx].rid;
1198                         SAM_USER_INFO_21 usr;
1199
1200                         fprintf(out_hnd, "User RID: %8x  User Name: %s\n",
1201                                           user_rid,
1202                                           info->dom.sam[user_idx].acct_name);
1203
1204                         if (request_user_info)
1205                         {
1206                                 /* send user info query, level 0x15 */
1207                                 if (get_samr_query_userinfo(smb_cli, fnum,
1208                                                         &info->dom.samr_pol_open_domain,
1209                                                         0x15, user_rid, &usr))
1210                                 {
1211                                         display_sam_user_info_21(out_hnd, ACTION_HEADER   , &usr);
1212                                         display_sam_user_info_21(out_hnd, ACTION_ENUMERATE, &usr);
1213                                         display_sam_user_info_21(out_hnd, ACTION_FOOTER   , &usr);
1214                                 }
1215                         }
1216
1217                         if (request_group_info)
1218                         {
1219                                 uint32 num_groups;
1220                                 DOM_GID gid[LSA_MAX_GROUPS];
1221
1222                                 /* send user group query */
1223                                 if (get_samr_query_usergroups(smb_cli, fnum,
1224                                                         &info->dom.samr_pol_open_domain,
1225                                                         user_rid, &num_groups, gid))
1226                                 {
1227                                 uint32 num_names;
1228                                 uint32  rid_mem[MAX_LOOKUP_SIDS];
1229                                 fstring name   [MAX_LOOKUP_SIDS];
1230                                 uint32  type   [MAX_LOOKUP_SIDS];
1231
1232                                 for (i = 0; i < num_groups; i++)
1233                                 {
1234                                         rid_mem[i] = gid[i].g_rid;
1235                                 }
1236
1237                                 if (samr_query_lookup_rids(smb_cli, fnum, 
1238                                                 &info->dom.samr_pol_open_domain, 0x3e8,
1239                                                 num_groups, rid_mem, 
1240                                                 &num_names, name, type))
1241                                 {
1242                                         display_group_members(out_hnd, ACTION_HEADER   , num_names, name, type);
1243                                         display_group_members(out_hnd, ACTION_ENUMERATE, num_names, name, type);
1244                                         display_group_members(out_hnd, ACTION_FOOTER   , num_names, name, type);
1245                                 }
1246                                 }
1247                         }
1248
1249                         if (request_alias_info)
1250                         {
1251                                 uint32 num_aliases;
1252                                 uint32 rid[LSA_MAX_GROUPS];
1253                                 DOM_SID als_sid;
1254
1255                                 sid_copy(&als_sid, &sid1);
1256                                 sid_append_rid(&als_sid, user_rid);
1257
1258                                 /* send user alias query */
1259                                 if (samr_query_useraliases(smb_cli, fnum,
1260                                                         &info->dom.samr_pol_open_domain,
1261                                                         &als_sid, &num_aliases, rid))
1262                                 {
1263                                 uint32 num_names;
1264                                 fstring name   [MAX_LOOKUP_SIDS];
1265                                 uint32  type   [MAX_LOOKUP_SIDS];
1266
1267                                 if (samr_query_lookup_rids(smb_cli, fnum, 
1268                                                 &info->dom.samr_pol_open_domain, 0x3e8,
1269                                                 num_aliases, rid, 
1270                                                 &num_names, name, type))
1271                                 {
1272                                         display_group_members(out_hnd, ACTION_HEADER   , num_names, name, type);
1273                                         display_group_members(out_hnd, ACTION_ENUMERATE, num_names, name, type);
1274                                         display_group_members(out_hnd, ACTION_FOOTER   , num_names, name, type);
1275                                 }
1276                         }
1277
1278                         /* send user alias query */
1279                         if (res1 && samr_query_useraliases(smb_cli, fnum,
1280                                                 &info->dom.samr_pol_open_builtindom,
1281                                                 &als_sid, &num_aliases, rid))
1282                         {
1283                                 uint32 num_names;
1284                                 fstring name   [MAX_LOOKUP_SIDS];
1285                                 uint32  type   [MAX_LOOKUP_SIDS];
1286
1287                                 if (samr_query_lookup_rids(smb_cli, fnum, 
1288                                                 &info->dom.samr_pol_open_builtindom, 0x3e8,
1289                                                 num_aliases, rid, 
1290                                                 &num_names, name, type))
1291                                 {
1292                                         display_group_members(out_hnd, ACTION_HEADER   , num_names, name, type);
1293                                         display_group_members(out_hnd, ACTION_ENUMERATE, num_names, name, type);
1294                                         display_group_members(out_hnd, ACTION_FOOTER   , num_names, name, type);
1295                                 }
1296                         }
1297                 }
1298         }
1299
1300         res1 = res1 ? samr_close(smb_cli, fnum,
1301                     &info->dom.samr_pol_open_builtindom) : False;
1302
1303         res = res ? samr_close(smb_cli, fnum,
1304                     &info->dom.samr_pol_open_domain) : False;
1305
1306         res = res ? samr_close(smb_cli, fnum,
1307                     &info->dom.samr_pol_connect) : False;
1308
1309         /* close the session */
1310         cli_nt_session_close(smb_cli, fnum);
1311
1312         if (info->dom.sam != NULL)
1313         {
1314                 free(info->dom.sam);
1315         }
1316
1317         if (res)
1318         {
1319                 DEBUG(5,("cmd_sam_enum_users: succeeded\n"));
1320         }
1321         else
1322         {
1323                 DEBUG(5,("cmd_sam_enum_users: failed\n"));
1324         }
1325 }
1326
1327
1328 /****************************************************************************
1329 experimental SAM user query.
1330 ****************************************************************************/
1331 void cmd_sam_query_user(struct client_info *info)
1332 {
1333         uint16 fnum;
1334         fstring srv_name;
1335         fstring domain;
1336         fstring sid;
1337         DOM_SID sid1;
1338         int user_idx = 0;  /* FIXME maybe ... */
1339         BOOL res = True;
1340         uint32 flags = 0x304; /* absolutely no idea. */
1341         fstring rid_str ;
1342         fstring info_str;
1343         uint32 user_rid = 0;
1344         uint32 info_level = 0x15;
1345
1346         SAM_USER_INFO_21 usr;
1347
1348         sid_to_string(sid, &info->dom.level5_sid);
1349         fstrcpy(domain, info->dom.level5_dom);
1350
1351         if (strlen(sid) == 0)
1352         {
1353                 fprintf(out_hnd, "please use 'lsaquery' first, to ascertain the SID\n");
1354                 return;
1355         }
1356
1357         string_to_sid(&sid1, sid);
1358
1359         fstrcpy(srv_name, "\\\\");
1360         fstrcat(srv_name, info->dest_host);
1361         strupper(srv_name);
1362
1363         if (next_token(NULL, rid_str , NULL, sizeof(rid_str )) &&
1364             next_token(NULL, info_str, NULL, sizeof(info_str)))
1365         {
1366                 user_rid   = strtoul(rid_str , (char**)NULL, 16);
1367                 info_level = strtoul(info_str, (char**)NULL, 10);
1368         }
1369
1370         fprintf(out_hnd, "SAM Query User: rid %x info level %d\n",
1371                           user_rid, info_level);
1372         fprintf(out_hnd, "From: %s To: %s Domain: %s SID: %s\n",
1373                           info->myhostname, srv_name, domain, sid);
1374
1375         /* open SAMR session.  negotiate credentials */
1376         res = res ? cli_nt_session_open(smb_cli, PIPE_SAMR, &fnum) : False;
1377
1378         /* establish a connection. */
1379         res = res ? samr_connect(smb_cli, fnum,
1380                                 srv_name, 0x00000020,
1381                                 &info->dom.samr_pol_connect) : False;
1382
1383         /* connect to the domain */
1384         res = res ? samr_open_domain(smb_cli, fnum,
1385                     &info->dom.samr_pol_connect, flags, &sid1,
1386                     &info->dom.samr_pol_open_domain) : False;
1387
1388         fprintf(out_hnd, "User RID: %8x  User Name: %s\n",
1389                           user_rid,
1390                           info->dom.sam[user_idx].acct_name);
1391
1392         /* send user info query, level */
1393         if (get_samr_query_userinfo(smb_cli, fnum,
1394                                         &info->dom.samr_pol_open_domain,
1395                                         info_level, user_rid, &usr))
1396         {
1397                 if (info_level == 0x15)
1398                 {
1399                         display_sam_user_info_21(out_hnd, ACTION_HEADER   , &usr);
1400                         display_sam_user_info_21(out_hnd, ACTION_ENUMERATE, &usr);
1401                         display_sam_user_info_21(out_hnd, ACTION_FOOTER   , &usr);
1402                 }
1403         }
1404
1405         res = res ? samr_close(smb_cli, fnum,
1406                     &info->dom.samr_pol_connect) : False;
1407
1408         res = res ? samr_close(smb_cli, fnum,
1409                     &info->dom.samr_pol_open_domain) : False;
1410
1411         /* close the session */
1412         cli_nt_session_close(smb_cli, fnum);
1413
1414         if (res)
1415         {
1416                 DEBUG(5,("cmd_sam_query_user: succeeded\n"));
1417         }
1418         else
1419         {
1420                 DEBUG(5,("cmd_sam_query_user: failed\n"));
1421         }
1422 }
1423
1424
1425 /****************************************************************************
1426 experimental SAM domain info query.
1427 ****************************************************************************/
1428 void cmd_sam_query_dominfo(struct client_info *info)
1429 {
1430         uint16 fnum;
1431         fstring srv_name;
1432         fstring domain;
1433         fstring sid;
1434         DOM_SID sid1;
1435         BOOL res = True;
1436         fstring info_str;
1437         uint32 switch_value = 2;
1438         uint32 flags = 0x304; /* absolutely no idea. */
1439
1440         sid_to_string(sid, &info->dom.level5_sid);
1441         fstrcpy(domain, info->dom.level5_dom);
1442
1443         if (strlen(sid) == 0)
1444         {
1445                 fprintf(out_hnd, "please use 'lsaquery' first, to ascertain the SID\n");
1446                 return;
1447         }
1448
1449         string_to_sid(&sid1, sid);
1450
1451         fstrcpy(srv_name, "\\\\");
1452         fstrcat(srv_name, info->dest_host);
1453         strupper(srv_name);
1454
1455         if (next_token(NULL, info_str, NULL, sizeof(info_str)))
1456         {
1457                 switch_value = strtoul(info_str, (char**)NULL, 10);
1458         }
1459
1460         fprintf(out_hnd, "SAM Query Domain Info: info level %d\n", switch_value);
1461         fprintf(out_hnd, "From: %s To: %s Domain: %s SID: %s\n",
1462                           info->myhostname, srv_name, domain, sid);
1463
1464         /* open SAMR session.  negotiate credentials */
1465         res = res ? cli_nt_session_open(smb_cli, PIPE_SAMR, &fnum) : False;
1466
1467         /* establish a connection. */
1468         res = res ? samr_connect(smb_cli, fnum, 
1469                                 srv_name, 0x00000020,
1470                                 &info->dom.samr_pol_connect) : False;
1471
1472         /* connect to the domain */
1473         res = res ? samr_open_domain(smb_cli, fnum, 
1474                     &info->dom.samr_pol_connect, flags, &sid1,
1475                     &info->dom.samr_pol_open_domain) : False;
1476
1477         /* send a samr 0x8 command */
1478         res = res ? samr_query_dom_info(smb_cli, fnum,
1479                     &info->dom.samr_pol_open_domain, switch_value) : False;
1480
1481         res = res ? samr_close(smb_cli, fnum,
1482                     &info->dom.samr_pol_connect) : False;
1483
1484         res = res ? samr_close(smb_cli, fnum, 
1485                     &info->dom.samr_pol_open_domain) : False;
1486
1487         /* close the session */
1488         cli_nt_session_close(smb_cli, fnum);
1489
1490         if (res)
1491         {
1492                 DEBUG(5,("cmd_sam_query_dominfo: succeeded\n"));
1493         }
1494         else
1495         {
1496                 DEBUG(5,("cmd_sam_query_dominfo: failed\n"));
1497         }
1498 }
1499
1500
1501 /****************************************************************************
1502 SAM aliases query.
1503 ****************************************************************************/
1504 void cmd_sam_enum_aliases(struct client_info *info)
1505 {
1506         uint16 fnum;
1507         fstring srv_name;
1508         fstring domain;
1509         fstring sid;
1510         DOM_SID sid1;
1511         BOOL res = True;
1512         BOOL request_member_info = False;
1513         uint32 flags = 0x200003f3; /* absolutely no idea. */
1514         fstring tmp;
1515         uint32 alias_idx;
1516
1517         sid_to_string(sid, &info->dom.level3_sid);
1518         fstrcpy(domain, info->dom.level3_dom);
1519 #if 0
1520         fstrcpy(sid   , "S-1-5-20");
1521 #endif
1522         if (strlen(sid) == 0)
1523         {
1524                 fprintf(out_hnd, "please use 'lsaquery' first, to ascertain the SID\n");
1525                 return;
1526         }
1527
1528         string_to_sid(&sid1, sid);
1529
1530         fstrcpy(srv_name, "\\\\");
1531         fstrcat(srv_name, info->dest_host);
1532         strupper(srv_name);
1533
1534         /* a bad way to do token parsing... */
1535         if (next_token(NULL, tmp, NULL, sizeof(tmp)))
1536         {
1537                 request_member_info |= strequal(tmp, "-m");
1538         }
1539
1540         fprintf(out_hnd, "SAM Enumerate Aliases\n");
1541         fprintf(out_hnd, "From: %s To: %s Domain: %s SID: %s\n",
1542                           info->myhostname, srv_name, domain, sid);
1543
1544         /* open SAMR session.  negotiate credentials */
1545         res = res ? cli_nt_session_open(smb_cli, PIPE_SAMR, &fnum) : False;
1546
1547         /* establish a connection. */
1548         res = res ? samr_connect(smb_cli, fnum,
1549                                 srv_name, 0x00000020,
1550                                 &info->dom.samr_pol_connect) : False;
1551
1552         /* connect to the domain */
1553         res = res ? samr_open_domain(smb_cli, fnum,
1554                     &info->dom.samr_pol_connect, flags, &sid1,
1555                     &info->dom.samr_pol_open_domain) : False;
1556
1557         info->dom.sam = NULL;
1558
1559         /* read some aliases */
1560         res = res ? samr_enum_dom_aliases(smb_cli, fnum,
1561                                 &info->dom.samr_pol_open_domain,
1562                                 0xffff,
1563                                 &info->dom.sam, &info->dom.num_sam_entries) : False;
1564
1565         if (res && info->dom.num_sam_entries == 0)
1566         {
1567                 fprintf(out_hnd, "No aliases\n");
1568         }
1569
1570
1571         for (alias_idx = 0; alias_idx < info->dom.num_sam_entries; alias_idx++)
1572         {
1573                 uint32 alias_rid = info->dom.sam[alias_idx].rid;
1574
1575                 fprintf(out_hnd, "Alias RID: %8x  Group Name: %s\n",
1576                                   alias_rid,
1577                                   info->dom.sam[alias_idx].acct_name);
1578
1579                 if (request_member_info)
1580                 {
1581                         uint32 num_aliases;
1582                         DOM_SID2 sid_mem[MAX_LOOKUP_SIDS];
1583
1584                         /* send user aliases query */
1585                         if (get_samr_query_aliasmem(smb_cli, fnum, 
1586                                 &info->dom.samr_pol_open_domain,
1587                                                 alias_rid, &num_aliases, sid_mem))
1588                         {
1589                                 uint16 fnum_lsa;
1590                                 BOOL res3 = True;
1591                                 BOOL res4 = True;
1592                                 char **names = NULL;
1593                                 int num_names = 0;
1594                                 DOM_SID **sids = NULL;
1595                                 int i;
1596
1597                                 if (num_aliases != 0)
1598                                 {
1599                                         sids = malloc(num_aliases * sizeof(DOM_SID*));
1600                                 }
1601
1602                                 res3 = sids != NULL;
1603                                 if (res3)
1604                                 {
1605                                         for (i = 0; i < num_aliases; i++)
1606                                         {
1607                                                 sids[i] = &sid_mem[i].sid;
1608                                         }
1609                                 }
1610
1611                                 /* open LSARPC session. */
1612                                 res3 = res3 ? cli_nt_session_open(smb_cli, PIPE_LSARPC, &fnum_lsa) : False;
1613
1614                                 /* lookup domain controller; receive a policy handle */
1615                                 res3 = res3 ? lsa_open_policy(smb_cli, fnum_lsa,
1616                                                         srv_name,
1617                                                         &info->dom.lsa_info_pol, True) : False;
1618
1619                                 /* send lsa lookup sids call */
1620                                 res4 = res3 ? lsa_lookup_sids(smb_cli, fnum_lsa, 
1621                                                                &info->dom.lsa_info_pol,
1622                                                                num_aliases, sids, 
1623                                                                &names, NULL, &num_names) : False;
1624
1625                                 res3 = res3 ? lsa_close(smb_cli, fnum_lsa, &info->dom.lsa_info_pol) : False;
1626
1627                                 cli_nt_session_close(smb_cli, fnum_lsa);
1628
1629                                 if (res4 && names != NULL)
1630                                 {
1631                                         display_alias_members(out_hnd, ACTION_HEADER   , num_names, names);
1632                                         display_alias_members(out_hnd, ACTION_ENUMERATE, num_names, names);
1633                                         display_alias_members(out_hnd, ACTION_FOOTER   , num_names, names);
1634                                 }
1635                                 if (names != NULL)
1636                                 {
1637                                         for (i = 0; i < num_names; i++)
1638                                         {
1639                                                 if (names[i] != NULL)
1640                                                 {
1641                                                         free(names[i]);
1642                                                 }
1643                                         }
1644                                         free(names);
1645                                 }
1646                                 if (sids != NULL)
1647                                 {
1648                                         free(sids);
1649                                 }
1650                         }
1651                 }
1652         }
1653
1654         res = res ? samr_close(smb_cli, fnum, 
1655                     &info->dom.samr_pol_connect) : False;
1656
1657         res = res ? samr_close(smb_cli, fnum,
1658                     &info->dom.samr_pol_open_domain) : False;
1659
1660         /* close the session */
1661         cli_nt_session_close(smb_cli, fnum);
1662
1663         if (info->dom.sam != NULL)
1664         {
1665                 free(info->dom.sam);
1666         }
1667
1668         if (res)
1669         {
1670                 DEBUG(5,("cmd_sam_enum_aliases: succeeded\n"));
1671         }
1672         else
1673         {
1674                 DEBUG(5,("cmd_sam_enum_aliases: failed\n"));
1675         }
1676 }
1677
1678 /****************************************************************************
1679 SAM groups query.
1680 ****************************************************************************/
1681 void cmd_sam_enum_groups(struct client_info *info)
1682 {
1683         uint16 fnum;
1684         fstring srv_name;
1685         fstring domain;
1686         fstring sid;
1687         DOM_SID sid1;
1688         BOOL res = True;
1689         BOOL request_member_info = False;
1690         uint32 flags = 0x200003f3; /* absolutely no idea. */
1691         fstring tmp;
1692         uint32 group_idx;
1693
1694         sid_copy(&sid1, &info->dom.level3_sid);
1695
1696         if (sid1.num_auths == 0)
1697         {
1698                 fprintf(out_hnd, "please use 'lsaquery' first, to ascertain the SID\n");
1699                 return;
1700         }
1701
1702         sid_to_string(sid, &sid1);
1703         fstrcpy(domain, info->dom.level3_dom);
1704
1705         fstrcpy(srv_name, "\\\\");
1706         fstrcat(srv_name, info->dest_host);
1707         strupper(srv_name);
1708
1709         /* a bad way to do token parsing... */
1710         if (next_token(NULL, tmp, NULL, sizeof(tmp)))
1711         {
1712                 request_member_info |= strequal(tmp, "-m");
1713         }
1714
1715         fprintf(out_hnd, "SAM Enumerate Groups\n");
1716         fprintf(out_hnd, "From: %s To: %s Domain: %s SID: %s\n",
1717                           info->myhostname, srv_name, domain, sid);
1718
1719         /* open SAMR session.  negotiate credentials */
1720         res = res ? cli_nt_session_open(smb_cli, PIPE_SAMR, &fnum) : False;
1721
1722         /* establish a connection. */
1723         res = res ? samr_connect(smb_cli, fnum,
1724                                 srv_name, 0x00000020,
1725                                 &info->dom.samr_pol_connect) : False;
1726
1727         /* connect to the domain */
1728         res = res ? samr_open_domain(smb_cli, fnum,
1729                     &info->dom.samr_pol_connect, flags, &sid1,
1730                     &info->dom.samr_pol_open_domain) : False;
1731
1732         info->dom.sam = NULL;
1733
1734         /* read some groups */
1735         res = res ? samr_enum_dom_groups(smb_cli, fnum,
1736                                 &info->dom.samr_pol_open_domain,
1737                                 0xffff,
1738                                 &info->dom.sam, &info->dom.num_sam_entries) : False;
1739
1740         if (res && info->dom.num_sam_entries == 0)
1741         {
1742                 fprintf(out_hnd, "No groups\n");
1743         }
1744
1745
1746         for (group_idx = 0; group_idx < info->dom.num_sam_entries; group_idx++)
1747         {
1748                 uint32 group_rid = info->dom.sam[group_idx].rid;
1749
1750                 fprintf(out_hnd, "Group RID: %8x  Group Name: %s\n",
1751                                   group_rid,
1752                                   info->dom.sam[group_idx].acct_name);
1753
1754                 if (request_member_info)
1755                 {
1756                         uint32 num_mem;
1757                         uint32 rid_mem[MAX_LOOKUP_SIDS];
1758                         uint32 attr_mem[MAX_LOOKUP_SIDS];
1759
1760                         /* get group members */
1761                         if (get_samr_query_groupmem(smb_cli, fnum, 
1762                                 &info->dom.samr_pol_open_domain,
1763                                 group_rid, &num_mem, rid_mem, attr_mem))
1764                         {
1765                                 BOOL res3 = True;
1766                                 int num_names = 0;
1767                                 fstring names[MAX_LOOKUP_SIDS];
1768                                 uint32 types[MAX_LOOKUP_SIDS];
1769
1770                                 res3 = samr_query_lookup_rids(smb_cli, fnum,
1771                                        &info->dom.samr_pol_open_domain, 1000,
1772                                        num_mem, rid_mem, &num_names, names, types);
1773
1774                                 if (res3)
1775                                 {
1776                                         display_group_members(out_hnd, ACTION_HEADER   , num_names, names, types);
1777                                         display_group_members(out_hnd, ACTION_ENUMERATE, num_names, names, types);
1778                                         display_group_members(out_hnd, ACTION_FOOTER   , num_names, names, types);
1779                                 }
1780                         }
1781                 }
1782         }
1783
1784         res = res ? samr_close(smb_cli, fnum,
1785                     &info->dom.samr_pol_open_domain) : False;
1786
1787         res = res ? samr_close(smb_cli, fnum, 
1788                     &info->dom.samr_pol_connect) : False;
1789
1790         /* close the session */
1791         cli_nt_session_close(smb_cli, fnum);
1792
1793         if (info->dom.sam != NULL)
1794         {
1795                 free(info->dom.sam);
1796         }
1797
1798         if (res)
1799         {
1800                 DEBUG(5,("cmd_sam_enum_groups: succeeded\n"));
1801         }
1802         else
1803         {
1804                 DEBUG(5,("cmd_sam_enum_groups: failed\n"));
1805         }
1806 }