2 Unix SMB/Netbios implementation.
4 NT Domain Authentication SMB / MSRPC client
5 Copyright (C) Andrew Tridgell 1994-2000
6 Copyright (C) Luke Kenneth Casson Leighton 1996-2000
7 Copyright (C) Jean-Francois Micouleau 1999-2000
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.
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.
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.
26 #include "rpc_parse.h"
27 #include "rpc_client.h"
28 #include "rpcclient.h"
30 extern int DEBUGLEVEL
;
36 extern struct user_creds
*usr_creds
;
38 /********************************************************************
39 initialize a spoolss NEW_BUFFER.
40 ********************************************************************/
41 static void init_buffer(NEW_BUFFER
*buffer
, uint32 size
)
43 buffer
->ptr
= (size
!=0)? 1:0;
45 buffer
->string_at_end
=size
;
46 prs_init(&buffer
->prs
, size
, 4, MARSHALL
);
47 buffer
->struct_start
= prs_offset(&buffer
->prs
);
50 static void decode_printer_info_0(NEW_BUFFER
*buffer
, uint32 returned
,
51 PRINTER_INFO_0
**info
)
56 inf
=(PRINTER_INFO_0
*)malloc(returned
*sizeof(PRINTER_INFO_0
));
58 buffer
->prs
.data_offset
=0;
60 for (i
=0; i
<returned
; i
++) {
61 new_smb_io_printer_info_0("", buffer
, &(inf
[i
]), 0);
67 static void decode_printer_info_1(NEW_BUFFER
*buffer
, uint32 returned
,
68 PRINTER_INFO_1
**info
)
73 inf
=(PRINTER_INFO_1
*)malloc(returned
*sizeof(PRINTER_INFO_1
));
75 buffer
->prs
.data_offset
=0;
77 for (i
=0; i
<returned
; i
++) {
78 new_smb_io_printer_info_1("", buffer
, &(inf
[i
]), 0);
84 static void decode_printer_info_2(NEW_BUFFER
*buffer
, uint32 returned
,
85 PRINTER_INFO_2
**info
)
90 inf
=(PRINTER_INFO_2
*)malloc(returned
*sizeof(PRINTER_INFO_2
));
92 buffer
->prs
.data_offset
=0;
94 for (i
=0; i
<returned
; i
++) {
95 /* a little initialization as we go */
96 inf
[i
].secdesc
= NULL
;
97 new_smb_io_printer_info_2("", buffer
, &(inf
[i
]), 0);
103 static void decode_printer_info_3(NEW_BUFFER
*buffer
, uint32 returned
,
104 PRINTER_INFO_3
**info
)
109 inf
=(PRINTER_INFO_3
*)malloc(returned
*sizeof(PRINTER_INFO_3
));
111 buffer
->prs
.data_offset
=0;
113 for (i
=0; i
<returned
; i
++) {
114 new_smb_io_printer_info_3("", buffer
, &(inf
[i
]), 0);
120 static void decode_printer_driver_1(NEW_BUFFER
*buffer
, uint32 returned
,
121 DRIVER_INFO_1
**info
)
126 inf
=(DRIVER_INFO_1
*)malloc(returned
*sizeof(DRIVER_INFO_1
));
128 buffer
->prs
.data_offset
=0;
130 for (i
=0; i
<returned
; i
++) {
131 new_smb_io_printer_driver_info_1("", buffer
, &(inf
[i
]), 0);
137 static void decode_printer_driver_2(NEW_BUFFER
*buffer
, uint32 returned
,
138 DRIVER_INFO_2
**info
)
143 inf
=(DRIVER_INFO_2
*)malloc(returned
*sizeof(DRIVER_INFO_2
));
145 buffer
->prs
.data_offset
=0;
147 for (i
=0; i
<returned
; i
++) {
148 new_smb_io_printer_driver_info_2("", buffer
, &(inf
[i
]), 0);
154 static void decode_printer_driver_3(NEW_BUFFER
*buffer
, uint32 returned
,
155 DRIVER_INFO_3
**info
)
160 inf
=(DRIVER_INFO_3
*)malloc(returned
*sizeof(DRIVER_INFO_3
));
162 buffer
->prs
.data_offset
=0;
164 for (i
=0; i
<returned
; i
++) {
165 new_smb_io_printer_driver_info_3("", buffer
, &(inf
[i
]), 0);
171 static void decode_printerdriverdir_info_1(NEW_BUFFER
*buffer
, DRIVER_DIRECTORY_1
*info
)
173 /* DRIVER_DIRECTORY_1 *inf;
175 inf=(DRIVER_DIRECTORY_1 *)malloc(returned*sizeof(DRIVER_DIRECTORY_1));
177 prs_set_offset(&buffer
->prs
, 0);
179 new_smb_io_driverdir_1("", buffer
, info
, 0);
186 /****************************************************************************
188 ****************************************************************************/
189 BOOL
msrpc_spoolss_enum_printers(char* srv_name
, uint32 flags
,
190 uint32 level
, PRINTER_INFO_CTR ctr
)
197 init_buffer(&buffer
, 0);
199 /* send a NULL buffer first */
200 status
=spoolss_enum_printers(flags
, srv_name
, level
, &buffer
, 0,
203 if (status
==ERROR_INSUFFICIENT_BUFFER
) {
204 init_buffer(&buffer
, needed
);
205 status
=spoolss_enum_printers(flags
, srv_name
, level
, &buffer
,
206 needed
, &needed
, &returned
);
209 report(out_hnd
, "\tstatus:[%d (%x)]\n", status
, status
);
211 if (status
!=NT_STATUS_NO_PROBLEMO
)
214 /* is there anything to process? */
219 decode_printer_info_1(&buffer
, returned
, &(ctr
.printers_1
));
222 decode_printer_info_2(&buffer
, returned
, &(ctr
.printers_2
));
225 decode_printer_info_3(&buffer
, returned
, &(ctr
.printers_3
));
229 display_printer_info_ctr(out_hnd
, ACTION_HEADER
, level
, returned
, ctr
);
230 display_printer_info_ctr(out_hnd
, ACTION_ENUMERATE
, level
, returned
, ctr
);
231 display_printer_info_ctr(out_hnd
, ACTION_FOOTER
, level
, returned
, ctr
);
237 /****************************************************************************
239 ****************************************************************************/
240 uint32
msrpc_spoolss_getprinterdata( const char* printer_name
,
242 const char* user_name
,
243 const char* value_name
,
253 UNISTR2 uni_val_name
;
255 DEBUG(4,("spoolgetdata - printer: %s server: %s user: %s value: %s\n",
256 printer_name
, station
, user_name
, value_name
));
258 if(!spoolss_open_printer_ex( printer_name
, 0, 0, station
, user_name
,
261 return NT_STATUS_ACCESS_DENIED
;
264 init_unistr2(&uni_val_name
, value_name
, 0);
266 init_buffer(buffer
, size
);
268 status
= spoolss_getprinterdata(&hnd
, &uni_val_name
, size
, type
, &size
,
271 if (status
== ERROR_INSUFFICIENT_BUFFER
)
274 init_buffer(buffer
, size
);
275 data
= prs_data_p(&buffer
->prs
);
276 status
= spoolss_getprinterdata(&hnd
, &uni_val_name
,
281 if (status
!= NT_STATUS_NO_PROBLEMO
) {
282 if (!spoolss_closeprinter(&hnd
))
283 return NT_STATUS_ACCESS_DENIED
;
289 fn(printer_name
, station
, level
, returned
, *ctr
);
295 /****************************************************************************
297 ****************************************************************************/
298 BOOL
msrpc_spoolss_enum_jobs( const char* printer_name
,
299 const char* station
, const char* user_name
,
301 void ***ctr
, JOB_INFO_FN(fn
))
309 uint32 numofjobs
=0xffff;
311 DEBUG(4,("spoolopen - printer: %s server: %s user: %s\n",
312 printer_name
, station
, user_name
));
314 if(!spoolss_open_printer_ex( printer_name
, 0, 0, station
, user_name
, &hnd
))
317 init_buffer(&buffer
, 0);
318 status
= spoolss_enum_jobs(&hnd
, firstjob
, numofjobs
, level
, &buffer
, 0, &needed
, &returned
);
320 if (status
== ERROR_INSUFFICIENT_BUFFER
)
322 init_buffer(&buffer
, needed
);
323 status
= spoolss_enum_jobs( &hnd
, firstjob
, numofjobs
, level
, &buffer
, needed
, &needed
, &returned
);
326 if (status
!=NT_STATUS_NO_PROBLEMO
) {
327 if (!spoolss_closeprinter(&hnd
))
333 fn(printer_name
, station
, level
, returned
, *ctr
);
339 /****************************************************************************
341 ****************************************************************************/
342 BOOL
msrpc_spoolss_enum_printerdata( const char* printer_name
,
343 const char* station
, const char* user_name
)
356 DEBUG(4,("spoolenum_printerdata - printer: %s\n", printer_name
));
358 if(!spoolss_open_printer_ex( printer_name
, 0, 0, station
, user_name
, &hnd
))
362 something is severly buggy about the use of
363 data, datalen, value, & valuelen */
364 status
= spoolss_enum_printerdata(&hnd
, 0, &valuelen
, value
,
365 &rvaluelen
, &type
, &datalen
,
371 value
=(uint16
*)malloc(valuelen
*sizeof(uint16
));
372 data
=(uint8
*)malloc(datalen
*sizeof(uint8
));
374 display_printer_enumdata(out_hnd
, ACTION_HEADER
, idx
, valuelen
,
375 value
, rvaluelen
, type
, datalen
, data
, rdatalen
);
379 status
= spoolss_enum_printerdata(&hnd
, idx
, &valuelen
,
380 value
, &rvaluelen
, &type
,
381 &datalen
, data
, &rdatalen
);
382 display_printer_enumdata(out_hnd
, ACTION_ENUMERATE
, idx
,
383 valuelen
, value
, rvaluelen
, type
,
384 datalen
, data
, rdatalen
);
387 } while (status
!= 0x0103); /* NO_MORE_ITEMS */
389 display_printer_enumdata(out_hnd
, ACTION_FOOTER
, idx
, valuelen
,
390 value
, rvaluelen
, type
, datalen
, data
, rdatalen
);
393 if (status
!=NT_STATUS_NO_PROBLEMO
) {
395 * the check on this if statement is redundant
396 * since is the status is bad we're going to
397 * return False anyways. The caller will be
398 * unable to determine if there really was a problem
399 * with the spoolss_closeprinter() call --jerry
401 spoolss_closeprinter(&hnd
);
408 /****************************************************************************
410 ****************************************************************************/
411 BOOL
msrpc_spoolss_getprinter( const char* printer_name
, const uint32 level
,
412 const char* station
, const char* user_name
,
413 PRINTER_INFO_CTR ctr
)
420 DEBUG(4,("spoolenum_getprinter - printer: %s\n", printer_name
));
422 if(!spoolss_open_printer_ex( printer_name
, "", PRINTER_ALL_ACCESS
, station
, user_name
, &hnd
))
425 init_buffer(&buffer
, 0);
427 status
= spoolss_getprinter(&hnd
, level
, &buffer
, 0, &needed
);
429 if (status
==ERROR_INSUFFICIENT_BUFFER
) {
430 init_buffer(&buffer
, needed
);
431 status
= spoolss_getprinter(&hnd
, level
, &buffer
, needed
, &needed
);
434 report(out_hnd
, "\tstatus:[%d (%x)]\n", status
, status
);
436 if (status
!=NT_STATUS_NO_PROBLEMO
)
441 decode_printer_info_0(&buffer
, 1, &(ctr
.printers_0
));
444 decode_printer_info_1(&buffer
, 1, &(ctr
.printers_1
));
447 decode_printer_info_2(&buffer
, 1, &(ctr
.printers_2
));
450 decode_printer_info_3(&buffer
, 1, &(ctr
.printers_3
));
454 display_printer_info_ctr(out_hnd
, ACTION_HEADER
, level
, 1, ctr
);
455 display_printer_info_ctr(out_hnd
, ACTION_ENUMERATE
, level
, 1, ctr
);
456 display_printer_info_ctr(out_hnd
, ACTION_FOOTER
, level
, 1, ctr
);
458 if (status
!=NT_STATUS_NO_PROBLEMO
) {
459 if (!spoolss_closeprinter(&hnd
))
467 /****************************************************************************
469 ****************************************************************************/
470 BOOL
msrpc_spoolss_getprinterdriver( const char* printer_name
,
471 const char *environment
, const uint32 level
,
472 const char* station
, const char* user_name
,
473 PRINTER_DRIVER_CTR ctr
)
480 DEBUG(4,("spoolenum_getprinterdriver - printer: %s\n", printer_name
));
482 if(!spoolss_open_printer_ex( printer_name
, "", PRINTER_ALL_ACCESS
, station
, user_name
, &hnd
))
485 init_buffer(&buffer
, 0);
487 status
= spoolss_getprinterdriver(&hnd
, environment
, level
, &buffer
, 0, &needed
);
489 if (status
==ERROR_INSUFFICIENT_BUFFER
) {
490 init_buffer(&buffer
, needed
);
491 status
= spoolss_getprinterdriver(&hnd
, environment
, level
, &buffer
, needed
, &needed
);
494 report(out_hnd
, "\tstatus:[%d (%x)]\n", status
, status
);
496 if (status
!=NT_STATUS_NO_PROBLEMO
)
501 decode_printer_driver_1(&buffer
, 1, &(ctr
.info1
));
504 decode_printer_driver_2(&buffer
, 1, &(ctr
.info2
));
507 decode_printer_driver_3(&buffer
, 1, &(ctr
.info3
));
511 display_printer_driver_ctr(out_hnd
, ACTION_HEADER
, level
, 1, ctr
);
512 display_printer_driver_ctr(out_hnd
, ACTION_ENUMERATE
, level
, 1, ctr
);
513 display_printer_driver_ctr(out_hnd
, ACTION_FOOTER
, level
, 1, ctr
);
515 if (status
!=NT_STATUS_NO_PROBLEMO
) {
516 if (!spoolss_closeprinter(&hnd
))
524 /****************************************************************************
526 ****************************************************************************/
527 BOOL
msrpc_spoolss_enumprinterdrivers( const char* srv_name
,
528 const char *environment
, const uint32 level
,
529 PRINTER_DRIVER_CTR ctr
)
536 DEBUG(4,("spoolenum_enumprinterdrivers - server: %s\n", srv_name
));
538 init_buffer(&buffer
, 0);
540 status
= spoolss_enum_printerdrivers(srv_name
, environment
,
541 level
, &buffer
, 0, &needed
, &returned
);
543 if (status
== ERROR_INSUFFICIENT_BUFFER
)
545 init_buffer(&buffer
, needed
);
546 status
= spoolss_enum_printerdrivers( srv_name
, environment
,
547 level
, &buffer
, needed
, &needed
, &returned
);
550 report(out_hnd
, "\tstatus:[%d (%x)]\n", status
, status
);
552 if (status
!=NT_STATUS_NO_PROBLEMO
)
559 decode_printer_driver_1(&buffer
, returned
, &(ctr
.info1
));
564 decode_printer_driver_2(&buffer
, returned
, &(ctr
.info2
));
569 decode_printer_driver_3(&buffer
, returned
, &(ctr
.info3
));
574 display_printer_driver_ctr(out_hnd
, ACTION_HEADER
, level
, returned
, ctr
);
575 display_printer_driver_ctr(out_hnd
, ACTION_ENUMERATE
, level
, returned
, ctr
);
576 display_printer_driver_ctr(out_hnd
, ACTION_FOOTER
, level
, returned
, ctr
);
581 /****************************************************************************
583 ****************************************************************************/
584 BOOL
msrpc_spoolss_getprinterdriverdir(char* srv_name
, char* env_name
, uint32 level
, DRIVER_DIRECTORY_CTR ctr
)
590 init_buffer(&buffer
, 0);
592 /* send a NULL buffer first */
593 status
=spoolss_getprinterdriverdir(srv_name
, env_name
, level
, &buffer
, 0, &needed
);
595 if (status
==ERROR_INSUFFICIENT_BUFFER
) {
596 init_buffer(&buffer
, needed
);
597 status
=spoolss_getprinterdriverdir(srv_name
, env_name
, level
, &buffer
, needed
, &needed
);
600 report(out_hnd
, "\tstatus:[%d (%x)]\n", status
, status
);
602 if (status
!=NT_STATUS_NO_PROBLEMO
)
607 decode_printerdriverdir_info_1(&buffer
, &(ctr
.driver
.info_1
));
611 display_printerdriverdir_info_ctr(out_hnd
, ACTION_HEADER
, level
, ctr
);
612 display_printerdriverdir_info_ctr(out_hnd
, ACTION_ENUMERATE
, level
, ctr
);
613 display_printerdriverdir_info_ctr(out_hnd
, ACTION_FOOTER
, level
, ctr
);