rpcclient functions for remaining samr and lsa functions. All functions
[sfrench/samba-autobuild/.git] / source3 / rpcclient / rpcclient.c
1 /* 
2    Unix SMB/Netbios implementation.
3    Version 2.2
4    RPC pipe client
5
6    Copyright (C) Tim Potter 2000
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 #include "includes.h"
24
25 extern int DEBUGLEVEL;
26         
27 /* Connect info */
28
29 pstring password;
30 pstring username;
31 pstring workgroup;
32 pstring server;
33
34 /* Various pipe commands */
35
36 extern struct cmd_set lsarpc_commands[];
37 extern struct cmd_set samr_commands[];
38 extern struct cmd_set spoolss_commands[];
39
40 DOM_SID domain_sid;
41
42 /* Fetch the SID for this domain */
43
44 void fetch_domain_sid(void)
45 {
46         struct cli_state cli;
47         POLICY_HND pol;
48         uint32 result = 0, info_class = 5;
49         struct ntuser_creds creds;
50         fstring domain_name;
51         static BOOL got_domain_sid;
52
53         if (got_domain_sid) return;
54
55         ZERO_STRUCT(cli);
56         init_rpcclient_creds(&creds);
57
58         if (cli_lsa_initialise(&cli, server, &creds) == NULL) {
59                 fprintf(stderr, "could not initialise lsa pipe\n");
60                 goto error;
61         }
62
63         if ((result = cli_lsa_open_policy(&cli, True, 
64                                           SEC_RIGHTS_MAXIMUM_ALLOWED,
65                                           &pol) != NT_STATUS_NOPROBLEMO)) {
66                 goto error;
67         }
68
69         if ((result = cli_lsa_query_info_policy(&cli, &pol, info_class, 
70                                                 domain_name, &domain_sid))
71             != NT_STATUS_NOPROBLEMO) {
72                 goto error;
73         }
74
75         got_domain_sid = True;
76
77         cli_lsa_close(&cli, &pol);
78         cli_lsa_shutdown(&cli);
79
80         return;
81
82  error:
83         fprintf(stderr, "could not obtain sid for domain %s\n", workgroup);
84
85         if (result != NT_STATUS_NOPROBLEMO) {
86                 fprintf(stderr, "error: %s\n", get_nt_error_msg(result));
87         }
88
89         exit(1);
90 }
91
92 /* Initialise client credentials for authenticated pipe access */
93
94 void init_rpcclient_creds(struct ntuser_creds *creds)
95 {
96         ZERO_STRUCTP(creds);
97         
98         if (lp_encrypted_passwords()) {
99                 pwd_make_lm_nt_16(&creds->pwd, password);
100         } else {
101                 pwd_set_cleartext(&creds->pwd, password);
102         }
103
104         fstrcpy(creds->user_name, username);
105         fstrcpy(creds->domain, workgroup);
106 }
107
108 /* List to hold groups of commands */
109
110 static struct cmd_list {
111         struct cmd_list *prev, *next;
112         struct cmd_set *cmd_set;
113 } *cmd_list;
114
115 static uint32 cmd_help(int argc, char **argv)
116 {
117         struct cmd_list *temp_list;
118
119         for (temp_list = cmd_list; temp_list; temp_list = temp_list->next) {
120                 struct cmd_set *temp_set = temp_list->cmd_set;
121
122                 while(temp_set->name) {
123                         printf("%s\t%s\n", temp_set->name,
124                                temp_set->description);
125                         temp_set++;
126                 }
127         }
128
129         return 0;
130 }
131
132 static uint32 cmd_debuglevel(int argc, char **argv)
133 {
134         if (argc > 2) {
135                 printf("Usage: %s [debuglevel]\n", argv[0]);
136                 return NT_STATUS_NOPROBLEMO;
137         }
138
139         if (argc == 2) {
140                 DEBUGLEVEL = atoi(argv[1]);
141         }
142
143         printf("debuglevel is %d\n", DEBUGLEVEL);
144
145         return NT_STATUS_NOPROBLEMO;
146 }
147
148 static uint32 cmd_quit(int argc, char **argv)
149 {
150         exit(0);
151 }
152
153 /* Build in rpcclient commands */
154
155 static struct cmd_set rpcclient_commands[] = {
156         { "help", cmd_help, "Print list of commands" },
157         { "debuglevel", cmd_debuglevel, "Set debug level" },
158         { "quit", cmd_quit, "Exit program" },
159         { "?", cmd_help, "Print list of commands" },
160
161         { NULL, NULL, NULL }
162 };
163
164 void add_command_set(struct cmd_set *cmd_set)
165 {
166         struct cmd_list *entry;
167
168         if (!(entry = (struct cmd_list *)malloc(sizeof(struct cmd_list)))) {
169                 DEBUG(0, ("out of memory\n"));
170                 return;
171         }
172
173         ZERO_STRUCTP(entry);
174
175         entry->cmd_set = cmd_set;
176         DLIST_ADD(cmd_list, entry);
177 }
178
179 static uint32 do_cmd(struct cmd_set *cmd_entry, char *cmd)
180 {
181         char *p = cmd, **argv = NULL;
182         uint32 result;
183         pstring buf;
184         int argc = 1, i;
185
186         next_token(&p, buf, " ", sizeof(buf));
187
188         /* Count number of arguments first time through the loop then
189            allocate memory and strdup them. */
190
191  again:
192         while(next_token(NULL, buf, " ", sizeof(buf))) {
193                 if (argv) {
194                         argv[argc] = strdup(buf);
195                 }
196                 
197                 argc++;
198         }
199                                 
200         if (!argv) {
201
202                 /* Create argument list */
203
204                 argv = (char **)malloc(sizeof(char *) * argc);
205
206                 if (!argv) {
207                         fprintf(stderr, "out of memoryx\n");
208                         return 0;
209                 }
210                                         
211                 p = cmd;
212                 next_token(&p, buf, " ", sizeof(buf));
213                 argv[0] = strdup(buf);
214                 argc = 1;
215                                         
216                 goto again;
217         }
218
219         /* Call the function */
220
221         result = cmd_entry->fn(argc, argv);
222                                 
223         /* Cleanup */
224
225         for (i = 0; i < argc; i++) {
226                 free(argv[i]);
227         }
228         
229         free(argv);
230         
231         return result;
232 }
233
234 /* Process a command entered at the prompt or as part of -c */
235
236 static uint32 process_cmd(char *cmd)
237 {
238         struct cmd_list *temp_list;
239         BOOL found = False;
240         pstring buf;
241         char *p = cmd;
242         uint32 result;
243
244         if (!next_token(&p, buf, " ", sizeof(buf))) {
245                 return 0;
246         }
247
248         /* Search for matching commands */
249
250         for (temp_list = cmd_list; temp_list; temp_list = temp_list->next) {
251                 struct cmd_set *temp_set = temp_list->cmd_set;
252
253                 while(temp_set->name) {
254                         if (strequal(buf, temp_set->name)) {
255                                 found = True;
256                                 result = do_cmd(temp_set, cmd);
257                                 goto done;
258                         }
259                         temp_set++;
260                 }
261         }
262
263  done:
264         if (!found && buf[0]) {
265                 printf("command not found: %s\n", buf);
266                 return 0;
267         }
268
269         if (result != 0) {
270                 printf("result was %s\n", get_nt_error_msg(result));
271         }
272
273         return result;
274 }
275
276 /* Print usage information */
277
278 static void usage(char *pname)
279 {
280         printf("Usage: %s server [options]\n", pname);
281
282         printf("\t-N                    don't ask for a password\n");
283         printf("\t-d debuglevel         set the debuglevel\n");
284         printf("\t-h                    Print this help message.\n");
285         printf("\t-U username           set the network username\n");
286         printf("\t-W workgroup          set the workgroup name\n");
287         printf("\t-c command string     execute semicolon separated cmds\n");
288         printf("\n");
289 }
290
291 /* Main function */
292
293  int main(int argc, char *argv[])
294 {
295         extern char *optarg;
296         extern int optind;
297         struct in_addr dest_ip;
298         extern pstring global_myname;
299         BOOL got_pass = False;
300         BOOL have_ip = False;
301         int opt;
302         pstring cmdstr = "", servicesf = CONFIGFILE;
303         extern FILE *dbf;
304
305         setlinebuf(stdout);
306         dbf = stderr;
307
308         setup_logging(argv[0], True);
309
310 #ifdef HAVE_LIBREADLINE
311         /* Allow conditional parsing of the ~/.inputrc file. */
312         rl_readline_name = "rpcclient";
313 #endif    
314         
315         DEBUGLEVEL = 2;
316
317         /* Load smb.conf file */
318
319         if (!lp_load(servicesf,True,False,False)) {
320                 fprintf(stderr, "Can't load %s\n", servicesf);
321         }
322
323         codepage_initialise(lp_client_code_page());
324         charset_initialise();
325         load_interfaces();
326
327         TimeInit();
328
329         get_myname((*global_myname)?NULL:global_myname);
330         strupper(global_myname);
331
332         /* Parse options */
333
334         if (argc < 2) {
335                 usage(argv[0]);
336                 return 0;
337         }
338
339         pstrcpy(server, argv[1]);
340
341         argv++;
342         argc--;
343
344         while ((opt = getopt(argc, argv, "s:Nd:I:U:W:c:")) != EOF) {
345                 switch (opt) {
346                 case 's':
347                         pstrcpy(servicesf, optarg);
348                         break;
349                 case 'N':
350                         got_pass = True;
351                         break;
352                 case 'd':
353                         DEBUGLEVEL = atoi(optarg);
354                         break;
355                 case 'I':
356                         dest_ip = *interpret_addr2(optarg);
357                         have_ip = True;
358                         break;
359                 case 'U': {
360                         char *lp;
361                         pstrcpy(username,optarg);
362                         if ((lp=strchr(username,'%'))) {
363                                 *lp = 0;
364                                 pstrcpy(password,lp+1);
365                                 got_pass = True;
366                                 memset(strchr(optarg,'%')+1,'X',strlen(password));
367                         }
368                         break;
369                 }
370                 case 'W':
371                         pstrcpy(workgroup, optarg);
372                         break;
373                 case 'c':
374                         pstrcpy(cmdstr, optarg);
375                         got_pass = True;
376                         break;
377                 case 'h':
378                 default:
379                         usage(argv[0]);
380                         exit(1);
381                 }
382         }
383
384         /* Load command lists */
385
386         add_command_set(rpcclient_commands);
387         add_command_set(lsarpc_commands);
388         add_command_set(samr_commands);
389         add_command_set(spoolss_commands);
390
391         /* Do anything specified with -c */
392
393         if (cmdstr[0]) {
394                 pstring cmd;
395                 char *p = cmdstr;
396                 uint32 result;
397
398                 while(next_token(&p, cmd, ";", sizeof(pstring))) {
399                         result = process_cmd(cmd);
400                 }
401
402                 return 0;
403         }
404
405         /* Loop around accepting commands */
406
407         while(1) {
408                 pstring prompt, cmd;
409                 uint32 result;
410
411                 ZERO_STRUCT(cmd);
412                 
413                 slprintf(prompt, sizeof(prompt) - 1, "rpcclient> ");
414
415 #if HAVE_READLINE
416                 cmd = readline(prompt);
417 #else
418                 printf("%s", prompt);
419
420                 if (!fgets(cmd, sizeof(cmd) - 1, stdin)) {
421                         break;
422                 }
423
424                 cmd[strlen(cmd) - 1] = '\0';
425 #endif
426                 result = process_cmd(cmd);
427         }
428
429         return 0;
430 }