2 Unix SMB/CIFS implementation.
3 test suite for spoolss rpc operations
5 Copyright (C) Guenther Deschner 2009-2010
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 3 of the License, or
10 (at your option) any later version.
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this program. If not, see <http://www.gnu.org/licenses/>.
21 /****************************************************************************
22 ****************************************************************************/
28 /****************************************************************************
29 ****************************************************************************/
31 static BOOL test_OpenPrinter(struct torture_context *tctx,
33 LPPRINTER_DEFAULTS defaults,
36 torture_comment(tctx, "Testing OpenPrinter(%s)", printername);
38 if (!OpenPrinter(printername, handle, defaults)) {
40 sprintf(tmp, "failed to open printer %s, error was: 0x%08x\n",
41 printername, GetLastError());
42 torture_fail(tctx, tmp);
48 /****************************************************************************
49 ****************************************************************************/
51 static BOOL test_ClosePrinter(struct torture_context *tctx,
54 torture_comment(tctx, "Testing ClosePrinter");
56 if (!ClosePrinter(handle)) {
58 sprintf(tmp, "failed to close printer, error was: %s\n",
59 errstr(GetLastError()));
60 torture_fail(tctx, tmp);
67 /****************************************************************************
68 ****************************************************************************/
70 static BOOL test_EnumPrinters(struct torture_context *tctx,
73 DWORD levels[] = { 1, 2, 5 };
74 DWORD success[] = { 1, 1, 1 };
76 DWORD flags = PRINTER_ENUM_NAME;
79 for (i=0; i < ARRAY_SIZE(levels); i++) {
86 torture_comment(tctx, "Testing EnumPrinters level %d", levels[i]);
88 EnumPrinters(flags, servername, levels[i], NULL, 0, &needed, &returned);
90 if (err == ERROR_INSUFFICIENT_BUFFER) {
92 buffer = malloc(needed);
93 torture_assert(tctx, buffer, "malloc failed");
94 if (!EnumPrinters(flags, servername, levels[i], buffer, needed, &needed, &returned)) {
99 sprintf(tmp, "EnumPrinters failed level %d on [%s] (buffer size = %d), error: %s\n",
100 levels[i], servername, needed, errstr(err));
102 torture_fail(tctx, tmp);
104 torture_warning(tctx, tmp);
109 print_printer_info_bylevel(levels[i], buffer, returned);
119 /****************************************************************************
120 ****************************************************************************/
122 static BOOL test_EnumDrivers(struct torture_context *tctx,
126 DWORD levels[] = { 1, 2, 3, 4, 5, 6 };
127 DWORD success[] = { 1, 1, 1, 1, 1, 1 };
129 LPBYTE buffer = NULL;
131 for (i=0; i < ARRAY_SIZE(levels); i++) {
138 torture_comment(tctx, "Testing EnumPrinterDrivers level %d", levels[i]);
140 EnumPrinterDrivers(servername, architecture, levels[i], NULL, 0, &needed, &returned);
141 err = GetLastError();
142 if (err == ERROR_INSUFFICIENT_BUFFER) {
144 buffer = malloc(needed);
145 torture_assert(tctx, buffer, "malloc failed");
146 if (!EnumPrinterDrivers(servername, architecture, levels[i], buffer, needed, &needed, &returned)) {
147 err = GetLastError();
151 sprintf(tmp, "EnumPrinterDrivers failed level %d on [%s] (buffer size = %d), error: %s\n",
152 levels[i], servername, needed, errstr(err));
154 torture_fail(tctx, tmp);
156 torture_warning(tctx, tmp);
167 /****************************************************************************
168 ****************************************************************************/
170 static BOOL test_EnumForms(struct torture_context *tctx,
174 DWORD levels[] = { 1, 2 };
175 DWORD success[] = { 1, 0 };
177 LPBYTE buffer = NULL;
179 for (i=0; i < ARRAY_SIZE(levels); i++) {
186 torture_comment(tctx, "Testing EnumForms level %d", levels[i]);
188 EnumForms(handle, levels[i], NULL, 0, &needed, &returned);
189 err = GetLastError();
190 if (err == ERROR_INSUFFICIENT_BUFFER) {
192 buffer = malloc(needed);
193 torture_assert(tctx, buffer, "malloc failed");
194 if (!EnumForms(handle, levels[i], buffer, needed, &needed, &returned)) {
195 err = GetLastError();
199 sprintf(tmp, "EnumForms failed level %d on [%s] (buffer size = %d), error: %s\n",
200 levels[i], servername, needed, errstr(err));
202 torture_fail(tctx, tmp);
204 torture_warning(tctx, tmp);
215 /****************************************************************************
216 ****************************************************************************/
218 static BOOL test_EnumPorts(struct torture_context *tctx,
221 DWORD levels[] = { 1, 2 };
222 DWORD success[] = { 1, 1 };
224 LPBYTE buffer = NULL;
226 for (i=0; i < ARRAY_SIZE(levels); i++) {
233 torture_comment(tctx, "Testing EnumPorts level %d", levels[i]);
235 EnumPorts(servername, levels[i], NULL, 0, &needed, &returned);
236 err = GetLastError();
237 if (err == ERROR_INSUFFICIENT_BUFFER) {
239 buffer = malloc(needed);
240 torture_assert(tctx, buffer, "malloc failed");
241 if (!EnumPorts(servername, levels[i], buffer, needed, &needed, &returned)) {
242 err = GetLastError();
246 sprintf(tmp, "EnumPorts failed level %d on [%s] (buffer size = %d), error: %s\n",
247 levels[i], servername, needed, errstr(err));
249 torture_fail(tctx, tmp);
251 torture_warning(tctx, tmp);
262 /****************************************************************************
263 ****************************************************************************/
265 static BOOL test_EnumMonitors(struct torture_context *tctx,
268 DWORD levels[] = { 1, 2 };
269 DWORD success[] = { 1, 1 };
271 LPBYTE buffer = NULL;
273 for (i=0; i < ARRAY_SIZE(levels); i++) {
280 torture_comment(tctx, "Testing EnumMonitors level %d", levels[i]);
282 EnumMonitors(servername, levels[i], NULL, 0, &needed, &returned);
283 err = GetLastError();
284 if (err == ERROR_INSUFFICIENT_BUFFER) {
286 buffer = malloc(needed);
287 torture_assert(tctx, buffer, "malloc failed");
288 if (!EnumMonitors(servername, levels[i], buffer, needed, &needed, &returned)) {
289 err = GetLastError();
293 sprintf(tmp, "EnumMonitors failed level %d on [%s] (buffer size = %d), error: %s\n",
294 levels[i], servername, needed, errstr(err));
296 torture_fail(tctx, tmp);
298 torture_warning(tctx, tmp);
309 /****************************************************************************
310 ****************************************************************************/
312 static BOOL test_EnumPrintProcessors(struct torture_context *tctx,
316 DWORD levels[] = { 1 };
317 DWORD success[] = { 1 };
319 LPBYTE buffer = NULL;
321 for (i=0; i < ARRAY_SIZE(levels); i++) {
328 torture_comment(tctx, "Testing EnumPrintProcessors level %d", levels[i]);
330 EnumPrintProcessors(servername, architecture, levels[i], NULL, 0, &needed, &returned);
331 err = GetLastError();
332 if (err == ERROR_INSUFFICIENT_BUFFER) {
334 buffer = malloc(needed);
335 torture_assert(tctx, buffer, "malloc failed");
336 if (!EnumPrintProcessors(servername, architecture, levels[i], buffer, needed, &needed, &returned)) {
337 err = GetLastError();
341 sprintf(tmp, "EnumPrintProcessors failed level %d on [%s] (buffer size = %d), error: %s\n",
342 levels[i], servername, needed, errstr(err));
344 torture_fail(tctx, tmp);
346 torture_warning(tctx, tmp);
357 /****************************************************************************
358 ****************************************************************************/
360 static BOOL test_EnumPrintProcessorDatatypes(struct torture_context *tctx,
363 DWORD levels[] = { 1 };
364 DWORD success[] = { 1 };
366 LPBYTE buffer = NULL;
368 for (i=0; i < ARRAY_SIZE(levels); i++) {
375 torture_comment(tctx, "Testing EnumPrintProcessorDatatypes level %d", levels[i]);
377 EnumPrintProcessorDatatypes(servername, "winprint", levels[i], NULL, 0, &needed, &returned);
378 err = GetLastError();
379 if (err == ERROR_INSUFFICIENT_BUFFER) {
381 buffer = malloc(needed);
382 torture_assert(tctx, buffer, "malloc failed");
383 if (!EnumPrintProcessorDatatypes(servername, "winprint", levels[i], buffer, needed, &needed, &returned)) {
384 err = GetLastError();
388 sprintf(tmp, "EnumPrintProcessorDatatypes failed level %d on [%s] (buffer size = %d), error: %s\n",
389 levels[i], servername, needed, errstr(err));
391 torture_fail(tctx, tmp);
393 torture_warning(tctx, tmp);
404 /****************************************************************************
405 ****************************************************************************/
407 static BOOL test_EnumPrinterKey(struct torture_context *tctx,
417 torture_comment(tctx, "Testing EnumPrinterKey(%s)", key);
419 err = EnumPrinterKey(handle, key, NULL, 0, &needed);
420 if (err == ERROR_MORE_DATA) {
421 buffer = (LPTSTR)malloc(needed);
422 torture_assert(tctx, buffer, "malloc failed");
423 err = EnumPrinterKey(handle, key, buffer, needed, &needed);
426 sprintf(tmp, "EnumPrinterKey(%s) failed on [%s] (buffer size = %d), error: %s\n",
427 key, servername, needed, errstr(err));
428 torture_fail(tctx, tmp);
432 print_printer_keys(buffer);
440 /****************************************************************************
441 ****************************************************************************/
443 static BOOL test_GetPrinter(struct torture_context *tctx,
447 DWORD levels[] = { 1, 2, 3, 4, 5, 6, 7, 8 };
448 DWORD success[] = { 1, 1, 1, 1, 1, 1, 1, 1 };
450 LPBYTE buffer = NULL;
452 for (i=0; i < ARRAY_SIZE(levels); i++) {
458 torture_comment(tctx, "Testing GetPrinter level %d", levels[i]);
460 GetPrinter(handle, levels[i], NULL, 0, &needed);
461 err = GetLastError();
462 if (err == ERROR_INSUFFICIENT_BUFFER) {
464 buffer = malloc(needed);
465 torture_assert(tctx, buffer, "malloc failed");
466 if (!GetPrinter(handle, levels[i], buffer, needed, &needed)) {
467 err = GetLastError();
471 sprintf(tmp, "GetPrinter failed level %d on [%s] (buffer size = %d), error: %s\n",
472 levels[i], printername, needed, errstr(err));
474 torture_fail(tctx, tmp);
476 torture_warning(tctx, tmp);
487 /****************************************************************************
488 ****************************************************************************/
490 static BOOL test_GetPrinterDriver(struct torture_context *tctx,
495 DWORD levels[] = { 1, 2, 3, 4, 5, 6, 8 };
496 DWORD success[] = { 1, 1, 1, 1, 1, 1, 1 };
498 LPBYTE buffer = NULL;
500 for (i=0; i < ARRAY_SIZE(levels); i++) {
506 torture_comment(tctx, "Testing GetPrinterDriver level %d", levels[i]);
508 GetPrinterDriver(handle, architecture, levels[i], NULL, 0, &needed);
509 err = GetLastError();
510 if (err == ERROR_INSUFFICIENT_BUFFER) {
512 buffer = malloc(needed);
513 torture_assert(tctx, buffer, "malloc failed");
514 if (!GetPrinterDriver(handle, architecture, levels[i], buffer, needed, &needed)) {
515 err = GetLastError();
519 sprintf(tmp, "GetPrinterDriver failed level %d on [%s] (buffer size = %d), error: %s\n",
520 levels[i], printername, needed, errstr(err));
522 torture_fail(tctx, tmp);
524 torture_warning(tctx, tmp);
536 /****************************************************************************
537 ****************************************************************************/
539 static BOOL test_EnumJobs(struct torture_context *tctx,
543 DWORD levels[] = { 1, 2, 3, 4 };
544 DWORD success[] = { 1, 1, 1, 1 };
546 LPBYTE buffer = NULL;
548 for (i=0; i < ARRAY_SIZE(levels); i++) {
555 torture_comment(tctx, "Testing EnumJobs level %d", levels[i]);
557 EnumJobs(handle, 0, 100, levels[i], NULL, 0, &needed, &returned);
558 err = GetLastError();
559 if (err == ERROR_INSUFFICIENT_BUFFER) {
561 buffer = malloc(needed);
562 torture_assert(tctx, buffer, "malloc failed");
563 if (!EnumJobs(handle, 0, 100, levels[i], buffer, needed, &needed, &returned)) {
564 err = GetLastError();
568 sprintf(tmp, "EnumJobs failed level %d on [%s] (buffer size = %d), error: %s\n",
569 levels[i], printername, needed, errstr(err));
571 torture_fail(tctx, tmp);
573 torture_warning(tctx, tmp);
584 /****************************************************************************
585 ****************************************************************************/
587 static BOOL test_OnePrinter(struct torture_context *tctx,
590 LPPRINTER_DEFAULTS defaults)
595 torture_comment(tctx, "Testing Printer %s", printername);
597 ret &= test_OpenPrinter(tctx, printername, defaults, &handle);
598 ret &= test_GetPrinter(tctx, printername, handle);
599 ret &= test_GetPrinterDriver(tctx, printername, architecture, handle);
600 ret &= test_EnumForms(tctx, printername, handle);
601 ret &= test_EnumJobs(tctx, printername, handle);
602 ret &= test_EnumPrinterKey(tctx, printername, handle, "");
603 ret &= test_EnumPrinterKey(tctx, printername, handle, "PrinterDriverData");
604 ret &= test_ClosePrinter(tctx, handle);
609 /****************************************************************************
610 ****************************************************************************/
612 static BOOL test_EachPrinter(struct torture_context *tctx,
615 LPPRINTER_DEFAULTS defaults)
622 DWORD flags = PRINTER_ENUM_NAME;
623 PPRINTER_INFO_1 buffer = NULL;
626 torture_comment(tctx, "Testing EnumPrinters level %d", 1);
628 EnumPrinters(flags, servername, 1, NULL, 0, &needed, &returned);
629 err = GetLastError();
630 if (err == ERROR_INSUFFICIENT_BUFFER) {
632 buffer = (PPRINTER_INFO_1)malloc(needed);
633 torture_assert(tctx, buffer, "malloc failed");
634 if (!EnumPrinters(flags, servername, 1, (LPBYTE)buffer, needed, &needed, &returned)) {
635 err = GetLastError();
639 sprintf(tmp, "EnumPrinters failed level %d on [%s] (buffer size = %d), error: %s\n",
640 1, servername, needed, errstr(err));
641 torture_fail(tctx, tmp);
644 for (i=0; i < returned; i++) {
645 ret &= test_OnePrinter(tctx, buffer[i].pName, architecture, defaults);
653 /****************************************************************************
654 ****************************************************************************/
656 static BOOL test_GetPrintProcessorDirectory(struct torture_context *tctx,
660 DWORD levels[] = { 1 };
661 DWORD success[] = { 1 };
663 LPBYTE buffer = NULL;
665 for (i=0; i < ARRAY_SIZE(levels); i++) {
671 torture_comment(tctx, "Testing GetPrintProcessorDirectory level %d", levels[i]);
673 GetPrintProcessorDirectory(servername, architecture, levels[i], NULL, 0, &needed);
674 err = GetLastError();
675 if (err == ERROR_INSUFFICIENT_BUFFER) {
677 buffer = malloc(needed);
678 torture_assert(tctx, buffer, "malloc failed");
679 if (!GetPrintProcessorDirectory(servername, architecture, levels[i], buffer, needed, &needed)) {
680 err = GetLastError();
684 sprintf(tmp, "GetPrintProcessorDirectory failed level %d on [%s] (buffer size = %d), error: %s\n",
685 levels[i], servername, needed, errstr(err));
687 torture_fail(tctx, tmp);
689 torture_warning(tctx, tmp);
700 /****************************************************************************
701 ****************************************************************************/
703 static BOOL test_GetPrinterDriverDirectory(struct torture_context *tctx,
707 DWORD levels[] = { 1 };
708 DWORD success[] = { 1 };
710 LPBYTE buffer = NULL;
712 for (i=0; i < ARRAY_SIZE(levels); i++) {
718 torture_comment(tctx, "Testing GetPrinterDriverDirectory level %d", levels[i]);
720 GetPrinterDriverDirectory(servername, architecture, levels[i], NULL, 0, &needed);
721 err = GetLastError();
722 if (err == ERROR_INSUFFICIENT_BUFFER) {
724 buffer = malloc(needed);
725 torture_assert(tctx, buffer, "malloc failed");
726 if (!GetPrinterDriverDirectory(servername, architecture, levels[i], buffer, needed, &needed)) {
727 err = GetLastError();
731 sprintf(tmp, "GetPrinterDriverDirectory failed level %d on [%s] (buffer size = %d), error: %s\n",
732 levels[i], servername, needed, errstr(err));
734 torture_fail(tctx, tmp);
736 torture_warning(tctx, tmp);
748 /****************************************************************************
749 ****************************************************************************/
751 int main(int argc, char *argv[])
755 LPSTR architecture = "Windows NT x86";
756 HANDLE server_handle;
757 PRINTER_DEFAULTS defaults_admin, defaults_use;
758 struct torture_context *tctx;
761 fprintf(stderr, "usage: %s <servername> [print]\n", argv[0]);
765 tctx = malloc(sizeof(struct torture_context));
767 fprintf(stderr, "out of memory\n");
770 memset(tctx, '\0', sizeof(*tctx));
772 servername = argv[1];
775 if (strcmp(argv[2], "print") == 0) {
780 defaults_admin.pDatatype = NULL;
781 defaults_admin.pDevMode = NULL;
782 defaults_admin.DesiredAccess = PRINTER_ACCESS_ADMINISTER;
784 defaults_use.pDatatype = NULL;
785 defaults_use.pDevMode = NULL;
786 defaults_use.DesiredAccess = PRINTER_ACCESS_USE;
788 ret &= test_EnumPrinters(tctx, servername);
789 ret &= test_EnumDrivers(tctx, servername, architecture);
790 ret &= test_OpenPrinter(tctx, servername, NULL, &server_handle);
791 /* ret &= test_EnumPrinterKey(tctx, servername, server_handle, ""); */
792 ret &= test_EnumForms(tctx, servername, server_handle);
793 ret &= test_ClosePrinter(tctx, server_handle);
794 ret &= test_EnumPorts(tctx, servername);
795 ret &= test_EnumMonitors(tctx, servername);
796 ret &= test_EnumPrintProcessors(tctx, servername, architecture);
797 ret &= test_EnumPrintProcessorDatatypes(tctx, servername);
798 ret &= test_GetPrintProcessorDirectory(tctx, servername, architecture);
799 ret &= test_GetPrinterDriverDirectory(tctx, servername, architecture);
800 ret &= test_EachPrinter(tctx, servername, architecture, NULL);
803 if (tctx->last_reason) {
804 fprintf(stderr, "failed: %s\n", tctx->last_reason);
810 printf("%s run successfully\n", argv[0]);