Some old stuff hanging around since the CIFS conference. Big cleanup of
[ira/wip.git] / source3 / rpcclient / cmd_reg.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    Copyright (C) Simo Sorce 2001
8    
9    This program is free software; you can redistribute it and/or modify
10    it under the terms of the GNU General Public License as published by
11    the Free Software Foundation; either version 2 of the License, or
12    (at your option) any later version.
13    
14    This program is distributed in the hope that it will be useful,
15    but WITHOUT ANY WARRANTY; without even the implied warranty of
16    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17    GNU General Public License for more details.
18    
19    You should have received a copy of the GNU General Public License
20    along with this program; if not, write to the Free Software
21    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
22 */
23
24 #include "includes.h"
25 #include "rpcclient.h"
26
27 /*
28  * keys.  of the form:
29  * ----
30  *
31  * [HKLM]|[HKU]\[parent_keyname_components]\[subkey]|[value]
32  *
33  * reg_getsubkey() splits this down into:
34  * [HKLM]|[HKU]\[parent_keyname_components] and [subkey]|[value]
35  *
36  * do_reg_connect() splits the left side down further into:
37  * [HKLM]|[HKU] and [parent_keyname_components].
38  *
39  * HKLM is short for HKEY_LOCAL_MACHINE
40  * HKU  is short for HKEY_USERS
41  *
42  * oh, and HKEY stands for "Hive Key".
43  *
44  */
45
46 #if 0 /* Simo: reg functions need to be updated to the new cmd interface */
47
48 /****************************************************************************
49 nt registry enum
50 ****************************************************************************/
51 static void cmd_reg_enum(struct client_info *info)
52 {
53         BOOL res = True;
54         BOOL res1 = True;
55         BOOL res2 = True;
56         int i;
57
58         POLICY_HND key_pol;
59         fstring full_keyname;
60         fstring key_name;
61
62         /*
63          * query key info
64          */
65
66         fstring key_class;
67         uint32 max_class_len = 0;
68         uint32 num_subkeys;
69         uint32 max_subkeylen;
70         uint32 max_subkeysize; 
71         uint32 num_values;
72         uint32 max_valnamelen;
73         uint32 max_valbufsize;
74         uint32 sec_desc;
75         NTTIME mod_time;
76
77         /*
78          * unknown 0x1a request
79          */
80
81         uint32 unk_1a_response;
82
83         DEBUG(5, ("cmd_reg_enum: smb_cli->fd:%d\n", smb_cli->fd));
84
85         if (!next_token_nr(NULL, full_keyname, NULL, sizeof(full_keyname)))
86         {
87                 fprintf(out_hnd, "regenum <key_name>\n");
88                 return;
89         }
90
91         /* open WINREG session. */
92         res = res ? cli_nt_session_open(smb_cli, PIPE_WINREG) : False;
93
94         /* open registry receive a policy handle */
95         res = res ? do_reg_connect(smb_cli, full_keyname, key_name,
96                                 &info->dom.reg_pol_connect) : False;
97
98         if ((*key_name) != 0)
99         {
100                 /* open an entry */
101                 res1 = res  ? do_reg_open_entry(smb_cli, &info->dom.reg_pol_connect,
102                                          key_name, 0x02000000, &key_pol) : False;
103         }
104         else
105         {
106                 memcpy(&key_pol, &info->dom.reg_pol_connect, sizeof(key_pol));
107         }
108
109         res1 = res1 ? do_reg_query_key(smb_cli,
110                                 &key_pol,
111                                 key_class, &max_class_len,
112                                 &num_subkeys, &max_subkeylen, &max_subkeysize,
113                                 &num_values, &max_valnamelen, &max_valbufsize,
114                                 &sec_desc, &mod_time) : False;
115
116         if (res1 && num_subkeys > 0)
117         {
118                 fprintf(out_hnd,"Subkeys\n");
119                 fprintf(out_hnd,"-------\n");
120         }
121
122         for (i = 0; i < num_subkeys; i++)
123         {
124                 /*
125                  * enumerate key
126                  */
127
128                 fstring enum_name;
129                 uint32 enum_unk1;
130                 uint32 enum_unk2;
131                 time_t key_mod_time;
132
133                 /* unknown 1a it */
134                 res2 = res1 ? do_reg_unknown_1a(smb_cli, &key_pol,
135                                         &unk_1a_response) : False;
136
137                 if (res2 && unk_1a_response != 5)
138                 {
139                         fprintf(out_hnd,"Unknown 1a response: %x\n", unk_1a_response);
140                 }
141
142                 /* enum key */
143                 res2 = res2 ? do_reg_enum_key(smb_cli, &key_pol,
144                                         i, enum_name,
145                                         &enum_unk1, &enum_unk2,
146                                         &key_mod_time) : False;
147                 
148                 if (res2)
149                 {
150                         display_reg_key_info(out_hnd, ACTION_HEADER   , enum_name, key_mod_time);
151                         display_reg_key_info(out_hnd, ACTION_ENUMERATE, enum_name, key_mod_time);
152                         display_reg_key_info(out_hnd, ACTION_FOOTER   , enum_name, key_mod_time);
153                 }
154
155         }
156
157         if (num_values > 0)
158         {
159                 fprintf(out_hnd,"Key Values\n");
160                 fprintf(out_hnd,"----------\n");
161         }
162
163         for (i = 0; i < num_values; i++)
164         {
165                 /*
166                  * enumerate key
167                  */
168
169                 uint32 val_type;
170                 BUFFER2 value;
171                 fstring val_name;
172
173                 /* unknown 1a it */
174                 res2 = res1 ? do_reg_unknown_1a(smb_cli, &key_pol,
175                                         &unk_1a_response) : False;
176
177                 if (res2 && unk_1a_response != 5)
178                 {
179                         fprintf(out_hnd,"Unknown 1a response: %x\n", unk_1a_response);
180                 }
181
182                 /* enum key */
183                 res2 = res2 ? do_reg_enum_val(smb_cli, &key_pol,
184                                         i, max_valnamelen, max_valbufsize,
185                                         val_name, &val_type, &value) : False;
186                 
187                 if (res2)
188                 {
189                         display_reg_value_info(out_hnd, ACTION_HEADER   , val_name, val_type, &value);
190                         display_reg_value_info(out_hnd, ACTION_ENUMERATE, val_name, val_type, &value);
191                         display_reg_value_info(out_hnd, ACTION_FOOTER   , val_name, val_type, &value);
192                 }
193         }
194
195         /* close the handles */
196         if ((*key_name) != 0)
197         {
198                 res1 = res1 ? do_reg_close(smb_cli, &key_pol) : False;
199         }
200         res  = res  ? do_reg_close(smb_cli, &info->dom.reg_pol_connect) : False;
201
202         /* close the session */
203         cli_nt_session_close(smb_cli);
204
205         if (res && res1 && res2)
206         {
207                 DEBUG(5,("cmd_reg_enum: query succeeded\n"));
208         }
209         else
210         {
211                 DEBUG(5,("cmd_reg_enum: query failed\n"));
212         }
213 }
214
215 /****************************************************************************
216 nt registry query key
217 ****************************************************************************/
218 static void cmd_reg_query_key(struct client_info *info)
219 {
220         BOOL res = True;
221         BOOL res1 = True;
222
223         POLICY_HND key_pol;
224         fstring full_keyname;
225         fstring key_name;
226
227         /*
228          * query key info
229          */
230
231         fstring key_class;
232         uint32 key_class_len = 0;
233         uint32 num_subkeys;
234         uint32 max_subkeylen;
235         uint32 max_subkeysize; 
236         uint32 num_values;
237         uint32 max_valnamelen;
238         uint32 max_valbufsize;
239         uint32 sec_desc;
240         NTTIME mod_time;
241
242         DEBUG(5, ("cmd_reg_enum: smb_cli->fd:%d\n", smb_cli->fd));
243
244         if (!next_token_nr(NULL, full_keyname, NULL, sizeof(full_keyname)))
245         {
246                 fprintf(out_hnd, "regquery key_name\n");
247                 return;
248         }
249
250         /* open WINREG session. */
251         res = res ? cli_nt_session_open(smb_cli, PIPE_WINREG) : False;
252
253         /* open registry receive a policy handle */
254         res = res ? do_reg_connect(smb_cli, full_keyname, key_name,
255                                 &info->dom.reg_pol_connect) : False;
256
257         if ((*key_name) != 0)
258         {
259                 /* open an entry */
260                 res1 = res  ? do_reg_open_entry(smb_cli, &info->dom.reg_pol_connect,
261                                          key_name, 0x02000000, &key_pol) : False;
262         }
263         else
264         {
265                 memcpy(&key_pol, &info->dom.reg_pol_connect, sizeof(key_pol));
266         }
267
268         res1 = res1 ? do_reg_query_key(smb_cli,
269                                 &key_pol,
270                                 key_class, &key_class_len,
271                                 &num_subkeys, &max_subkeylen, &max_subkeysize,
272                                 &num_values, &max_valnamelen, &max_valbufsize,
273                                 &sec_desc, &mod_time) : False;
274
275         if (res1 && key_class_len != 0)
276         {
277                 res1 = res1 ? do_reg_query_key(smb_cli,
278                                 &key_pol,
279                                 key_class, &key_class_len,
280                                 &num_subkeys, &max_subkeylen, &max_subkeysize,
281                                 &num_values, &max_valnamelen, &max_valbufsize,
282                                 &sec_desc, &mod_time) : False;
283         }
284
285         if (res1)
286         {
287                 fprintf(out_hnd,"Registry Query Info Key\n");
288                 fprintf(out_hnd,"key class: %s\n", key_class);
289                 fprintf(out_hnd,"subkeys, max_len, max_size: %d %d %d\n", num_subkeys, max_subkeylen, max_subkeysize);
290                 fprintf(out_hnd,"vals, max_len, max_size: 0x%x 0x%x 0x%x\n", num_values, max_valnamelen, max_valbufsize);
291                 fprintf(out_hnd,"sec desc: 0x%x\n", sec_desc);
292                 fprintf(out_hnd,"mod time: %s\n", http_timestring(nt_time_to_unix(&mod_time)));
293         }
294
295         /* close the handles */
296         if ((*key_name) != 0)
297         {
298                 res1 = res1 ? do_reg_close(smb_cli, &key_pol) : False;
299         }
300         res  = res  ? do_reg_close(smb_cli, &info->dom.reg_pol_connect) : False;
301
302         /* close the session */
303         cli_nt_session_close(smb_cli);
304
305         if (res && res1)
306         {
307                 DEBUG(5,("cmd_reg_query: query succeeded\n"));
308         }
309         else
310         {
311                 DEBUG(5,("cmd_reg_query: query failed\n"));
312         }
313 }
314
315 /****************************************************************************
316 nt registry create value
317 ****************************************************************************/
318 static void cmd_reg_create_val(struct client_info *info)
319 {
320         BOOL res = True;
321         BOOL res3 = True;
322         BOOL res4 = True;
323
324         POLICY_HND parent_pol;
325         fstring full_keyname;
326         fstring keyname;
327         fstring parent_name;
328         fstring val_name;
329         fstring tmp;
330         uint32 val_type;
331         BUFFER3 value;
332
333 #if 0
334         uint32 unk_0;
335         uint32 unk_1;
336         /* query it */
337         res1 = res1 ? do_reg_query_info(smb_cli, &val_pol,
338                                 val_name, *val_type) : False;
339 #endif
340
341         DEBUG(5, ("cmd_reg_create_val: smb_cli->fd:%d\n", smb_cli->fd));
342
343         if (!next_token_nr(NULL, full_keyname, NULL, sizeof(full_keyname)))
344         {
345                 fprintf(out_hnd, "regcreate <val_name> <val_type> <val>\n");
346                 return;
347         }
348
349         reg_get_subkey(full_keyname, keyname, val_name);
350
351         if (keyname[0] == 0 || val_name[0] == 0)
352         {
353                 fprintf(out_hnd, "invalid key name\n");
354                 return;
355         }
356         
357         if (!next_token_nr(NULL, tmp, NULL, sizeof(tmp)))
358         {
359                 fprintf(out_hnd, "regcreate <val_name> <val_type (1|4)> <val>\n");
360                 return;
361         }
362
363         val_type = atoi(tmp);
364
365         if (val_type != 1 && val_type != 3 && val_type != 4)
366         {
367                 fprintf(out_hnd, "val_type 1=UNISTR, 3=BYTES, 4=DWORD supported\n");
368                 return;
369         }
370
371         if (!next_token_nr(NULL, tmp, NULL, sizeof(tmp)))
372         {
373                 fprintf(out_hnd, "regcreate <val_name> <val_type (1|4)> <val>\n");
374                 return;
375         }
376
377         switch (val_type)
378         {
379                 case 0x01: /* UNISTR */
380                 {
381                         init_buffer3_str(&value, tmp, strlen(tmp)+1);
382                         break;
383                 }
384                 case 0x03: /* BYTES */
385                 {
386                         init_buffer3_hex(&value, tmp);
387                         break;
388                 }
389                 case 0x04: /* DWORD */
390                 {
391                         uint32 tmp_val;
392                         if (strnequal(tmp, "0x", 2))
393                         {
394                                 tmp_val = strtol(tmp, (char**)NULL, 16);
395                         }
396                         else
397                         {
398                                 tmp_val = strtol(tmp, (char**)NULL, 10);
399                         }
400                         init_buffer3_uint32(&value, tmp_val);
401                         break;
402                 }
403                 default:
404                 {
405                         fprintf(out_hnd, "i told you i only deal with UNISTR, DWORD and BYTES!\n");
406                         return;
407                 }
408         }
409                 
410         DEBUG(10,("key data:\n"));
411         dump_data(10, (char *)value.buffer, value.buf_len);
412
413         /* open WINREG session. */
414         res = res ? cli_nt_session_open(smb_cli, PIPE_WINREG) : False;
415
416         /* open registry receive a policy handle */
417         res = res ? do_reg_connect(smb_cli, keyname, parent_name,
418                                 &info->dom.reg_pol_connect) : False;
419
420         if ((*val_name) != 0)
421         {
422                 /* open an entry */
423                 res3 = res  ? do_reg_open_entry(smb_cli, &info->dom.reg_pol_connect,
424                                          parent_name, 0x02000000, &parent_pol) : False;
425         }
426         else
427         {
428                 memcpy(&parent_pol, &info->dom.reg_pol_connect, sizeof(parent_pol));
429         }
430
431         /* create an entry */
432         res4 = res3 ? do_reg_create_val(smb_cli, &parent_pol,
433                                  val_name, val_type, &value) : False;
434
435         /* flush the modified key */
436         res4 = res4 ? do_reg_flush_key(smb_cli, &parent_pol) : False;
437
438         /* close the val handle */
439         if ((*val_name) != 0)
440         {
441                 res3 = res3 ? do_reg_close(smb_cli, &parent_pol) : False;
442         }
443
444         /* close the registry handles */
445         res  = res  ? do_reg_close(smb_cli, &info->dom.reg_pol_connect) : False;
446
447         /* close the session */
448         cli_nt_session_close(smb_cli);
449
450         if (res && res3 && res4)
451         {
452                 DEBUG(5,("cmd_reg_create_val: query succeeded\n"));
453                 fprintf(out_hnd,"OK\n");
454         }
455         else
456         {
457                 DEBUG(5,("cmd_reg_create_val: query failed\n"));
458         }
459 }
460
461 /****************************************************************************
462 nt registry delete value
463 ****************************************************************************/
464 static void cmd_reg_delete_val(struct client_info *info)
465 {
466         BOOL res = True;
467         BOOL res3 = True;
468         BOOL res4 = True;
469
470         POLICY_HND parent_pol;
471         fstring full_keyname;
472         fstring keyname;
473         fstring parent_name;
474         fstring val_name;
475
476         DEBUG(5, ("cmd_reg_delete_val: smb_cli->fd:%d\n", smb_cli->fd));
477
478         if (!next_token_nr(NULL, full_keyname, NULL, sizeof(full_keyname)))
479         {
480                 fprintf(out_hnd, "regdelete <val_name>\n");
481                 return;
482         }
483
484         reg_get_subkey(full_keyname, keyname, val_name);
485
486         if (keyname[0] == 0 || val_name[0] == 0)
487         {
488                 fprintf(out_hnd, "invalid key name\n");
489                 return;
490         }
491         
492         /* open WINREG session. */
493         res = res ? cli_nt_session_open(smb_cli, PIPE_WINREG) : False;
494
495         /* open registry receive a policy handle */
496         res = res ? do_reg_connect(smb_cli, keyname, parent_name,
497                                 &info->dom.reg_pol_connect) : False;
498
499         if ((*val_name) != 0)
500         {
501                 /* open an entry */
502                 res3 = res  ? do_reg_open_entry(smb_cli, &info->dom.reg_pol_connect,
503                                          parent_name, 0x02000000, &parent_pol) : False;
504         }
505         else
506         {
507                 memcpy(&parent_pol, &info->dom.reg_pol_connect, sizeof(parent_pol));
508         }
509
510         /* delete an entry */
511         res4 = res3 ? do_reg_delete_val(smb_cli, &parent_pol, val_name) : False;
512
513         /* flush the modified key */
514         res4 = res4 ? do_reg_flush_key(smb_cli, &parent_pol) : False;
515
516         /* close the key handle */
517         res3 = res3 ? do_reg_close(smb_cli, &parent_pol) : False;
518
519         /* close the registry handles */
520         res  = res  ? do_reg_close(smb_cli, &info->dom.reg_pol_connect) : False;
521
522         /* close the session */
523         cli_nt_session_close(smb_cli);
524
525         if (res && res3 && res4)
526         {
527                 DEBUG(5,("cmd_reg_delete_val: query succeeded\n"));
528                 fprintf(out_hnd,"OK\n");
529         }
530         else
531         {
532                 DEBUG(5,("cmd_reg_delete_val: query failed\n"));
533         }
534 }
535
536 /****************************************************************************
537 nt registry delete key
538 ****************************************************************************/
539 static void cmd_reg_delete_key(struct client_info *info)
540 {
541         BOOL res = True;
542         BOOL res3 = True;
543         BOOL res4 = True;
544
545         POLICY_HND parent_pol;
546         fstring full_keyname;
547         fstring parent_name;
548         fstring key_name;
549         fstring subkey_name;
550
551         DEBUG(5, ("cmd_reg_delete_key: smb_cli->fd:%d\n", smb_cli->fd));
552
553         if (!next_token_nr(NULL, full_keyname, NULL, sizeof(full_keyname)))
554         {
555                 fprintf(out_hnd, "regdeletekey <key_name>\n");
556                 return;
557         }
558
559         reg_get_subkey(full_keyname, parent_name, subkey_name);
560
561         if (parent_name[0] == 0 || subkey_name[0] == 0)
562         {
563                 fprintf(out_hnd, "invalid key name\n");
564                 return;
565         }
566         
567         /* open WINREG session. */
568         res = res ? cli_nt_session_open(smb_cli, PIPE_WINREG) : False;
569
570         /* open registry receive a policy handle */
571         res = res ? do_reg_connect(smb_cli, parent_name, key_name,
572                                 &info->dom.reg_pol_connect) : False;
573
574         if ((*key_name) != 0)
575         {
576                 /* open an entry */
577                 res3 = res  ? do_reg_open_entry(smb_cli, &info->dom.reg_pol_connect,
578                                          key_name, 0x02000000, &parent_pol) : False;
579         }
580         else
581         {
582                 memcpy(&parent_pol, &info->dom.reg_pol_connect, sizeof(parent_pol));
583         }
584
585         /* create an entry */
586         res4 = res3 ? do_reg_delete_key(smb_cli, &parent_pol, subkey_name) : False;
587
588         /* flush the modified key */
589         res4 = res4 ? do_reg_flush_key(smb_cli, &parent_pol) : False;
590
591         /* close the key handle */
592         if ((*key_name) != 0)
593         {
594                 res3 = res3 ? do_reg_close(smb_cli, &parent_pol) : False;
595         }
596
597         /* close the registry handles */
598         res  = res  ? do_reg_close(smb_cli, &info->dom.reg_pol_connect) : False;
599
600         /* close the session */
601         cli_nt_session_close(smb_cli);
602
603         if (res && res3 && res4)
604         {
605                 DEBUG(5,("cmd_reg_delete_key: query succeeded\n"));
606                 fprintf(out_hnd,"OK\n");
607         }
608         else
609         {
610                 DEBUG(5,("cmd_reg_delete_key: query failed\n"));
611         }
612 }
613
614 /****************************************************************************
615 nt registry create key
616 ****************************************************************************/
617 static void cmd_reg_create_key(struct client_info *info)
618 {
619         BOOL res = True;
620         BOOL res3 = True;
621         BOOL res4 = True;
622
623         POLICY_HND parent_pol;
624         POLICY_HND key_pol;
625         fstring full_keyname;
626         fstring parent_key;
627         fstring parent_name;
628         fstring key_name;
629         fstring key_class;
630         SEC_ACCESS sam_access;
631
632         DEBUG(5, ("cmd_reg_create_key: smb_cli->fd:%d\n", smb_cli->fd));
633
634         if (!next_token_nr(NULL, full_keyname, NULL, sizeof(full_keyname)))
635         {
636                 fprintf(out_hnd, "regcreate <key_name> [key_class]\n");
637                 return;
638         }
639
640         reg_get_subkey(full_keyname, parent_key, key_name);
641
642         if (parent_key[0] == 0 || key_name[0] == 0)
643         {
644                 fprintf(out_hnd, "invalid key name\n");
645                 return;
646         }
647         
648         if (!next_token_nr(NULL, key_class, NULL, sizeof(key_class)))
649         {
650                 memset(key_class, 0, sizeof(key_class));
651         }
652
653         /* set access permissions */
654         sam_access.mask = SEC_RIGHTS_READ;
655
656         /* open WINREG session. */
657         res = res ? cli_nt_session_open(smb_cli, PIPE_WINREG) : False;
658
659         /* open registry receive a policy handle */
660         res = res ? do_reg_connect(smb_cli, parent_key, parent_name,
661                                 &info->dom.reg_pol_connect) : False;
662
663         if ((*parent_name) != 0)
664         {
665                 /* open an entry */
666                 res3 = res  ? do_reg_open_entry(smb_cli, &info->dom.reg_pol_connect,
667                                          parent_name, 0x02000000, &parent_pol) : False;
668         }
669         else
670         {
671                 memcpy(&parent_pol, &info->dom.reg_pol_connect, sizeof(parent_pol));
672         }
673
674         /* create an entry */
675         res4 = res3 ? do_reg_create_key(smb_cli, &parent_pol,
676                                  key_name, key_class, &sam_access, &key_pol) : False;
677
678         /* flush the modified key */
679         res4 = res4 ? do_reg_flush_key(smb_cli, &parent_pol) : False;
680
681         /* close the key handle */
682         res4 = res4 ? do_reg_close(smb_cli, &key_pol) : False;
683
684         /* close the key handle */
685         if ((*parent_name) != 0)
686         {
687                 res3 = res3 ? do_reg_close(smb_cli, &parent_pol) : False;
688         }
689
690         /* close the registry handles */
691         res  = res  ? do_reg_close(smb_cli, &info->dom.reg_pol_connect) : False;
692
693         /* close the session */
694         cli_nt_session_close(smb_cli);
695
696         if (res && res3 && res4)
697         {
698                 DEBUG(5,("cmd_reg_create_key: query succeeded\n"));
699                 fprintf(out_hnd,"OK\n");
700         }
701         else
702         {
703                 DEBUG(5,("cmd_reg_create_key: query failed\n"));
704         }
705 }
706
707 /****************************************************************************
708 nt registry security info
709 ****************************************************************************/
710 static void cmd_reg_test_key_sec(struct client_info *info)
711 {
712         BOOL res = True;
713         BOOL res3 = True;
714         BOOL res4 = True;
715
716         POLICY_HND key_pol;
717         fstring full_keyname;
718         fstring key_name;
719
720         /*
721          * security info
722          */
723
724         uint32 sec_buf_size;
725         SEC_DESC_BUF *psdb;
726
727         DEBUG(5, ("cmd_reg_get_key_sec: smb_cli->fd:%d\n", smb_cli->fd));
728
729         if (!next_token_nr(NULL, full_keyname, NULL, sizeof(full_keyname)))
730         {
731                 fprintf(out_hnd, "reggetsec <key_name>\n");
732                 return;
733         }
734
735         /* open WINREG session. */
736         res = res ? cli_nt_session_open(smb_cli, PIPE_WINREG) : False;
737
738         /* open registry receive a policy handle */
739         res = res ? do_reg_connect(smb_cli, full_keyname, key_name,
740                                 &info->dom.reg_pol_connect) : False;
741
742         if ((*key_name) != 0)
743         {
744                 /* open an entry */
745                 res3 = res  ? do_reg_open_entry(smb_cli, &info->dom.reg_pol_connect,
746                                          key_name, 0x02000000, &key_pol) : False;
747         }
748         else
749         {
750                 memcpy(&key_pol, &info->dom.reg_pol_connect, sizeof(key_pol));
751         }
752
753         /* open an entry */
754         res3 = res ? do_reg_open_entry(smb_cli, &info->dom.reg_pol_connect,
755                                  key_name, 0x02000000, &key_pol) : False;
756
757         /* query key sec info.  first call sets sec_buf_size. */
758
759         sec_buf_size = 0;
760         res4 = res3 ? do_reg_get_key_sec(smb_cli, &key_pol,
761                                 &sec_buf_size, &psdb) : False;
762         
763         free_sec_desc_buf(&psdb);
764
765         res4 = res4 ? do_reg_get_key_sec(smb_cli, &key_pol,
766                                 &sec_buf_size, &psdb) : False;
767
768         if (res4 && psdb->len > 0 && psdb->sec != NULL)
769         {
770                 display_sec_desc(out_hnd, ACTION_HEADER   , psdb->sec);
771                 display_sec_desc(out_hnd, ACTION_ENUMERATE, psdb->sec);
772                 display_sec_desc(out_hnd, ACTION_FOOTER   , psdb->sec);
773
774                 res4 = res4 ? do_reg_set_key_sec(smb_cli, &key_pol, psdb) : False;
775         }
776
777         free_sec_desc_buf(&psdb);
778
779         /* close the key handle */
780         if ((*key_name) != 0)
781         {
782                 res3 = res3 ? do_reg_close(smb_cli, &key_pol) : False;
783         }
784
785         /* close the registry handles */
786         res  = res  ? do_reg_close(smb_cli, &info->dom.reg_pol_connect) : False;
787
788         /* close the session */
789         cli_nt_session_close(smb_cli);
790
791         if (res && res3 && res4)
792         {
793                 DEBUG(5,("cmd_reg_test2: query succeeded\n"));
794                 fprintf(out_hnd,"Registry Test2\n");
795         }
796         else
797         {
798                 DEBUG(5,("cmd_reg_test2: query failed\n"));
799         }
800 }
801
802 /****************************************************************************
803 nt registry security info
804 ****************************************************************************/
805 static void cmd_reg_get_key_sec(struct client_info *info)
806 {
807         BOOL res = True;
808         BOOL res3 = True;
809         BOOL res4 = True;
810
811         POLICY_HND key_pol;
812         fstring full_keyname;
813         fstring key_name;
814
815         /*
816          * security info
817          */
818
819         uint32 sec_buf_size;
820         SEC_DESC_BUF *psdb;
821
822         DEBUG(5, ("cmd_reg_get_key_sec: smb_cli->fd:%d\n", smb_cli->fd));
823
824         if (!next_token_nr(NULL, full_keyname, NULL, sizeof(full_keyname)))
825         {
826                 fprintf(out_hnd, "reggetsec <key_name>\n");
827                 return;
828         }
829
830         /* open WINREG session. */
831         res = res ? cli_nt_session_open(smb_cli, PIPE_WINREG) : False;
832
833         /* open registry receive a policy handle */
834         res = res ? do_reg_connect(smb_cli, full_keyname, key_name,
835                                 &info->dom.reg_pol_connect) : False;
836
837         if ((*key_name) != 0)
838         {
839                 /* open an entry */
840                 res3 = res  ? do_reg_open_entry(smb_cli, &info->dom.reg_pol_connect,
841                                          key_name, 0x02000000, &key_pol) : False;
842         }
843         else
844         {
845                 memcpy(&key_pol, &info->dom.reg_pol_connect, sizeof(key_pol));
846         }
847
848         /* open an entry */
849         res3 = res ? do_reg_open_entry(smb_cli, &info->dom.reg_pol_connect,
850                                  key_name, 0x02000000, &key_pol) : False;
851
852         /* Get the size. */
853         sec_buf_size = 0;
854         res4 = res3 ? do_reg_get_key_sec(smb_cli, &key_pol,
855                                 &sec_buf_size, &psdb) : False;
856         
857         free_sec_desc_buf(&psdb);
858
859         res4 = res4 ? do_reg_get_key_sec(smb_cli, &key_pol,
860                                 &sec_buf_size, &psdb) : False;
861
862         if (res4 && psdb->len > 0 && psdb->sec != NULL)
863         {
864                 display_sec_desc(out_hnd, ACTION_HEADER   , psdb->sec);
865                 display_sec_desc(out_hnd, ACTION_ENUMERATE, psdb->sec);
866                 display_sec_desc(out_hnd, ACTION_FOOTER   , psdb->sec);
867         }
868
869         free_sec_desc_buf(&psdb);
870
871         /* close the key handle */
872         if ((*key_name) != 0)
873         {
874                 res3 = res3 ? do_reg_close(smb_cli, &key_pol) : False;
875         }
876
877         /* close the registry handles */
878         res  = res  ? do_reg_close(smb_cli, &info->dom.reg_pol_connect) : False;
879
880         /* close the session */
881         cli_nt_session_close(smb_cli);
882
883         if (res && res3 && res4)
884         {
885                 DEBUG(5,("cmd_reg_get_key_sec: query succeeded\n"));
886         }
887         else
888         {
889                 DEBUG(5,("cmd_reg_get_key_sec: query failed\n"));
890         }
891 }
892
893 #endif /* 0 */
894
895 /****************************************************************************
896 nt registry shutdown
897 ****************************************************************************/
898 static NTSTATUS cmd_reg_shutdown(struct cli_state *cli, TALLOC_CTX *mem_ctx,
899                                  int argc, char **argv)
900 {
901         NTSTATUS result = NT_STATUS_UNSUCCESSFUL;
902         fstring msg;
903         uint32 timeout = 20;
904         uint16 flgs = 0;
905         int opt;
906         int ret;
907         char *srv_name;
908
909         ret = asprintf (&srv_name, "\\\\%s", cli->desthost);
910         if (ret < 0) {
911                 DEBUG(0,("cmd_reg_shutdown: Not enough memory!\n"));
912                 return NT_STATUS_UNSUCCESSFUL;
913         }
914         strupper(srv_name);
915
916         *msg = 0;
917         optind = 0; /* TODO: test if this hack works on other systems too --simo */
918
919         while ((opt = getopt(argc, argv, "m:t:rf")) != EOF)
920         {
921                 fprintf (stderr, "[%s]\n", argv[argc-1]);
922         
923                 switch (opt)
924                 {
925                         case 'm':
926                         {
927                                 safe_strcpy(msg, optarg, sizeof(msg)-1);
928                                 fprintf (stderr, "[%s|%s]\n", optarg, msg);
929                                 break;
930                         }
931                         case 't':
932                         {
933                                 timeout = atoi(optarg);
934                                 fprintf (stderr, "[%s|%d]\n", optarg, timeout);
935                         break;
936                         }
937                         case 'r':
938                         {
939                                 flgs |= 0x100;
940                         break;
941                         }
942                         case 'f':
943                         {
944                                 flgs |= 0x001;
945                                 break;
946                         }
947                 }
948         }
949
950         /* create an entry */
951         result = cli_reg_shutdown(cli, mem_ctx, srv_name, msg, timeout, flgs);
952
953         if (NT_STATUS_IS_OK(result))
954                 DEBUG(5,("cmd_reg_shutdown: query succeeded\n"));
955         else
956                 DEBUG(5,("cmd_reg_shutdown: query failed\n"));
957
958         return result;
959 }
960
961 /****************************************************************************
962 abort a shutdown
963 ****************************************************************************/
964 static NTSTATUS cmd_reg_abort_shutdown(struct cli_state *cli, 
965                                        TALLOC_CTX *mem_ctx, int argc, 
966                                        char **argv)
967 {
968         NTSTATUS result = NT_STATUS_UNSUCCESSFUL;
969         int ret;
970         char *srv_name;
971
972         ret = asprintf(&srv_name, "\\\\%s", cli->desthost);
973         if (ret < 0) {
974                 DEBUG(0,("cmd_reg_shutdown: Not enough memory!\n"));
975                 return NT_STATUS_UNSUCCESSFUL;
976         }
977         strupper(srv_name);
978
979         result = cli_reg_abort_shutdown(cli, mem_ctx, srv_name);
980
981         if (NT_STATUS_IS_OK(result))
982                 DEBUG(5,("cmd_reg_abort_shutdown: query succeeded\n"));
983         else
984                 DEBUG(5,("cmd_reg_abort_shutdown: query failed\n"));
985
986         return result;
987 }
988
989
990 /* List of commands exported by this module */
991 struct cmd_set reg_commands[] = {
992
993         { "REG"  },
994
995         { "shutdown",           cmd_reg_shutdown,               PIPE_WINREG, "Remote Shutdown",
996                                 "[-m message] [-t timeout] [-r] [-f] (-r == reboot, -f == force)" },
997                                 
998         { "abortshutdown",      cmd_reg_abort_shutdown,         PIPE_WINREG, "Abort Shutdown",
999                                 "" },                           
1000 /*
1001         { "regenum",            cmd_reg_enum,                   "Registry Enumeration",
1002                                 "<keyname>" },
1003                                 
1004         { "regdeletekey",       cmd_reg_delete_key,             "Registry Key Delete",
1005                                 "<keyname>" },
1006                                 
1007         { "regcreatekey",       cmd_reg_create_key,             "Registry Key Create",
1008                                 "<keyname> [keyclass]" },
1009                                 
1010         { "regqueryval",        cmd_reg_query_info,             "Registry Value Query",
1011                                 "<valname>" },
1012                                 
1013         { "regquerykey",        cmd_reg_query_key,              "Registry Key Query",
1014                                 "<keyname>" },
1015                                 
1016         { "regdeleteval",       cmd_reg_delete_val,             "Registry Value Delete",
1017                                 "<valname>" },
1018         
1019         { "regcreateval",       cmd_reg_create_val,             "Registry Key Create",
1020                                 "<valname> <valtype> <value>" },
1021         
1022         { "reggetsec",          cmd_reg_get_key_sec,            "Registry Key Security",
1023                                 "<keyname>" },
1024         
1025         { "regtestsec",         cmd_reg_test_key_sec,           "Test Registry Key Security",
1026                                 "<keyname>" },
1027 */
1028         { NULL }
1029 };