2 Unix SMB/CIFS implementation.
3 test suite for SMB printing operations
5 Copyright (C) Guenther Deschner 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/>.
22 #include "libcli/raw/libcliraw.h"
23 #include "libcli/libcli.h"
24 #include "torture/torture.h"
25 #include "torture/util.h"
26 #include "system/filesys.h"
28 #include "torture/smbtorture.h"
29 #include "torture/util.h"
30 #include "../librpc/gen_ndr/rap.h"
31 #include "torture/rap/proto.h"
32 #include "param/param.h"
35 #define TORTURE_PRINT_FILE "torture_print_file"
37 static bool print_printjob(struct torture_context *tctx,
38 struct smbcli_tree *tree)
45 torture_comment(tctx, "creating printjob %s\n", TORTURE_PRINT_FILE);
47 fnum = smbcli_open(tree, TORTURE_PRINT_FILE, O_RDWR|O_CREAT|O_TRUNC, DENY_NONE);
49 torture_fail(tctx, "failed to open file");
52 str = talloc_asprintf(tctx, "TortureTestPage: %d\nData\n",0);
54 data = data_blob_string_const(str);
56 size_written = smbcli_write(tree, fnum, 0, data.data, 0, data.length);
57 if (size_written != data.length) {
58 torture_fail(tctx, "failed to write file");
61 torture_assert_ntstatus_ok(tctx,
62 smbcli_close(tree, fnum),
63 "failed to close file");
68 static bool test_raw_print(struct torture_context *tctx,
69 struct smbcli_state *cli)
71 return print_printjob(tctx, cli->tree);
74 static bool test_netprintqenum(struct torture_context *tctx,
75 struct smbcli_state *cli)
77 struct rap_NetPrintQEnum r;
79 uint16_t levels[] = { 0, 1, 2, 3, 4, 5 };
81 for (i=0; i < ARRAY_SIZE(levels); i++) {
83 r.in.level = levels[i];
87 "Testing rap_NetPrintQEnum level %d\n", r.in.level);
89 torture_assert_ntstatus_ok(tctx,
90 smbcli_rap_netprintqenum(cli->tree, tctx, &r),
91 "smbcli_rap_netprintqenum failed");
92 torture_assert_werr_ok(tctx, W_ERROR(r.out.status),
93 "failed to enum printq");
95 for (q=0; q<r.out.count; q++) {
98 printf("%s\n", r.out.info[q].info0.PrintQName);
107 static bool test_netprintqgetinfo(struct torture_context *tctx,
108 struct smbcli_state *cli)
110 struct rap_NetPrintQGetInfo r;
111 struct rap_NetPrintQEnum r_enum;
113 uint16_t levels[] = { 0, 1, 2, 3, 4, 5 };
116 r_enum.in.bufsize = 8192;
118 torture_assert_ntstatus_ok(tctx,
119 smbcli_rap_netprintqenum(cli->tree, tctx, &r_enum),
120 "failed to enum printq");
121 torture_assert_werr_ok(tctx, W_ERROR(r_enum.out.status),
122 "failed to enum printq");
124 for (p=0; p < r_enum.out.count; p++) {
126 for (i=0; i < ARRAY_SIZE(levels); i++) {
128 r.in.level = levels[i];
130 r.in.PrintQueueName = r_enum.out.info[p].info5.PrintQueueName;
132 torture_comment(tctx, "Testing rap_NetPrintQGetInfo(%s) level %d\n",
133 r.in.PrintQueueName, r.in.level);
135 torture_assert_ntstatus_ok(tctx,
136 smbcli_rap_netprintqgetinfo(cli->tree, tctx, &r),
137 "smbcli_rap_netprintqgetinfo failed");
139 switch (r.in.level) {
141 printf("%s\n", r.out.info.info0.PrintQName);
150 static bool test_netprintjob_pause(struct torture_context *tctx,
151 struct smbcli_state *cli,
154 struct rap_NetPrintJobPause r;
158 torture_comment(tctx, "Testing rap_NetPrintJobPause(%d)\n", r.in.JobID);
160 torture_assert_ntstatus_ok(tctx,
161 smbcli_rap_netprintjobpause(cli->tree, tctx, &r),
162 "smbcli_rap_netprintjobpause failed");
167 static bool test_netprintjob_continue(struct torture_context *tctx,
168 struct smbcli_state *cli,
171 struct rap_NetPrintJobContinue r;
175 torture_comment(tctx, "Testing rap_NetPrintJobContinue(%d)\n", r.in.JobID);
177 torture_assert_ntstatus_ok(tctx,
178 smbcli_rap_netprintjobcontinue(cli->tree, tctx, &r),
179 "smbcli_rap_netprintjobcontinue failed");
184 static bool test_netprintjob_delete(struct torture_context *tctx,
185 struct smbcli_state *cli,
188 struct rap_NetPrintJobDelete r;
192 torture_comment(tctx, "Testing rap_NetPrintJobDelete(%d)\n", r.in.JobID);
194 torture_assert_ntstatus_ok(tctx,
195 smbcli_rap_netprintjobdelete(cli->tree, tctx, &r),
196 "smbcli_rap_netprintjobdelete failed");
201 static bool test_netprintjob(struct torture_context *tctx,
202 struct smbcli_state *cli)
204 uint16_t job_id = 400;
207 test_netprintjob_pause(tctx, cli, job_id),
208 "failed to pause job");
210 test_netprintjob_continue(tctx, cli, job_id),
211 "failed to continue job");
213 test_netprintjob_delete(tctx, cli, job_id),
214 "failed to delete job");
219 static bool test_netprintq_pause(struct torture_context *tctx,
220 struct smbcli_state *cli,
221 const char *PrintQueueName)
223 struct rap_NetPrintQueuePause r;
225 r.in.PrintQueueName = PrintQueueName;
227 torture_comment(tctx, "Testing rap_NetPrintQueuePause(%s)\n", r.in.PrintQueueName);
229 torture_assert_ntstatus_ok(tctx,
230 smbcli_rap_netprintqueuepause(cli->tree, tctx, &r),
231 "smbcli_rap_netprintqueuepause failed");
232 torture_assert_werr_ok(tctx, W_ERROR(r.out.status),
233 "smbcli_rap_netprintqueuepause failed");
238 static bool test_netprintq_resume(struct torture_context *tctx,
239 struct smbcli_state *cli,
240 const char *PrintQueueName)
242 struct rap_NetPrintQueueResume r;
244 r.in.PrintQueueName = PrintQueueName;
246 torture_comment(tctx, "Testing rap_NetPrintQueueResume(%s)\n", r.in.PrintQueueName);
248 torture_assert_ntstatus_ok(tctx,
249 smbcli_rap_netprintqueueresume(cli->tree, tctx, &r),
250 "smbcli_rap_netprintqueueresume failed");
251 torture_assert_werr_ok(tctx, W_ERROR(r.out.status),
252 "smbcli_rap_netprintqueueresume failed");
257 static bool test_netprintq(struct torture_context *tctx,
258 struct smbcli_state *cli)
260 struct rap_NetPrintQEnum r;
266 torture_assert_ntstatus_ok(tctx,
267 smbcli_rap_netprintqenum(cli->tree, tctx, &r),
268 "failed to enum printq");
269 torture_assert_werr_ok(tctx, W_ERROR(r.out.status),
270 "failed to enum printq");
272 for (i=0; i < r.out.count; i++) {
274 const char *printqname = r.out.info[i].info5.PrintQueueName;
277 test_netprintq_pause(tctx, cli, printqname),
278 "failed to pause print queue");
281 test_netprintq_resume(tctx, cli, printqname),
282 "failed to resume print queue");
288 static bool test_netprintjobenum_args(struct torture_context *tctx,
289 struct smbcli_state *cli,
290 const char *PrintQueueName,
293 union rap_printj_info **info_p)
295 struct rap_NetPrintJobEnum r;
297 r.in.PrintQueueName = PrintQueueName;
301 torture_comment(tctx,
302 "Testing rap_NetPrintJobEnum(%s) level %d\n", r.in.PrintQueueName, r.in.level);
304 torture_assert_ntstatus_ok(tctx,
305 smbcli_rap_netprintjobenum(cli->tree, tctx, &r),
306 "smbcli_rap_netprintjobenum failed");
309 *count_p = r.out.count;
312 *info_p = r.out.info;
318 static bool test_netprintjobenum_one(struct torture_context *tctx,
319 struct smbcli_state *cli,
320 const char *PrintQueueName)
322 struct rap_NetPrintJobEnum r;
324 uint16_t levels[] = { 0, 1, 2 };
326 r.in.PrintQueueName = PrintQueueName;
329 for (i=0; i < ARRAY_SIZE(levels); i++) {
331 r.in.level = levels[i];
333 torture_comment(tctx,
334 "Testing rap_NetPrintJobEnum(%s) level %d\n", r.in.PrintQueueName, r.in.level);
336 torture_assert_ntstatus_ok(tctx,
337 smbcli_rap_netprintjobenum(cli->tree, tctx, &r),
338 "smbcli_rap_netprintjobenum failed");
344 static bool test_netprintjobgetinfo_byid(struct torture_context *tctx,
345 struct smbcli_state *cli,
348 struct rap_NetPrintJobGetInfo r;
349 uint16_t levels[] = { 0, 1, 2 };
355 for (i=0; i < ARRAY_SIZE(levels); i++) {
357 r.in.level = levels[i];
359 torture_comment(tctx, "Testing rap_NetPrintJobGetInfo(%d) level %d\n", r.in.JobID, r.in.level);
361 torture_assert_ntstatus_ok(tctx,
362 smbcli_rap_netprintjobgetinfo(cli->tree, tctx, &r),
363 "smbcli_rap_netprintjobgetinfo failed");
369 static bool test_netprintjobsetinfo_byid(struct torture_context *tctx,
370 struct smbcli_state *cli,
373 struct rap_NetPrintJobSetInfo r;
374 uint16_t levels[] = { 0, 1, 2 };
376 const char *comment = "tortured by samba";
379 r.in.bufsize = strlen(comment);
380 r.in.ParamNum = RAP_PARAM_JOBCOMMENT;
381 r.in.Param.string = comment;
383 for (i=0; i < ARRAY_SIZE(levels); i++) {
385 r.in.level = levels[i];
387 torture_comment(tctx, "Testing rap_NetPrintJobSetInfo(%d) level %d\n", r.in.JobID, r.in.level);
389 torture_assert_ntstatus_ok(tctx,
390 smbcli_rap_netprintjobsetinfo(cli->tree, tctx, &r),
391 "smbcli_rap_netprintjobsetinfo failed");
398 static bool test_netprintjobgetinfo_byqueue(struct torture_context *tctx,
399 struct smbcli_state *cli,
400 const char *PrintQueueName)
402 struct rap_NetPrintJobEnum r;
405 r.in.PrintQueueName = PrintQueueName;
409 torture_assert_ntstatus_ok(tctx,
410 smbcli_rap_netprintjobenum(cli->tree, tctx, &r),
411 "failed to enumerate jobs");
413 for (i=0; i < r.out.count; i++) {
416 test_netprintjobgetinfo_byid(tctx, cli, r.out.info[i].info0.JobID),
417 "failed to get job info");
423 static bool test_netprintjobsetinfo_byqueue(struct torture_context *tctx,
424 struct smbcli_state *cli,
425 const char *PrintQueueName)
427 struct rap_NetPrintJobEnum r;
430 r.in.PrintQueueName = PrintQueueName;
434 torture_assert_ntstatus_ok(tctx,
435 smbcli_rap_netprintjobenum(cli->tree, tctx, &r),
436 "failed to enumerate jobs");
438 for (i=0; i < r.out.count; i++) {
441 test_netprintjobsetinfo_byid(tctx, cli, r.out.info[i].info0.JobID),
442 "failed to set job info");
448 static bool test_netprintjobenum(struct torture_context *tctx,
449 struct smbcli_state *cli)
451 struct rap_NetPrintQEnum r;
457 torture_assert_ntstatus_ok(tctx,
458 smbcli_rap_netprintqenum(cli->tree, tctx, &r),
459 "failed to enum printq");
460 torture_assert_werr_ok(tctx, W_ERROR(r.out.status),
461 "failed to enum printq");
463 for (i=0; i < r.out.count; i++) {
465 const char *printqname = r.out.info[i].info5.PrintQueueName;
468 test_netprintjobenum_one(tctx, cli, printqname),
469 "failed to enumerate printjobs on print queue");
475 static bool test_netprintjobgetinfo(struct torture_context *tctx,
476 struct smbcli_state *cli)
478 struct rap_NetPrintQEnum r;
484 torture_assert_ntstatus_ok(tctx,
485 smbcli_rap_netprintqenum(cli->tree, tctx, &r),
486 "failed to enum printq");
487 torture_assert_werr_ok(tctx, W_ERROR(r.out.status),
488 "failed to enum printq");
490 for (i=0; i < r.out.count; i++) {
492 const char *printqname = r.out.info[i].info5.PrintQueueName;
495 test_netprintjobgetinfo_byqueue(tctx, cli, printqname),
496 "failed to enumerate printjobs on print queue");
502 static bool test_netprintjobsetinfo(struct torture_context *tctx,
503 struct smbcli_state *cli)
505 struct rap_NetPrintQEnum r;
511 torture_assert_ntstatus_ok(tctx,
512 smbcli_rap_netprintqenum(cli->tree, tctx, &r),
513 "failed to enum printq");
514 torture_assert_werr_ok(tctx, W_ERROR(r.out.status),
515 "failed to enum printq");
517 for (i=0; i < r.out.count; i++) {
519 const char *printqname = r.out.info[i].info5.PrintQueueName;
522 test_netprintjobsetinfo_byqueue(tctx, cli, printqname),
523 "failed to set printjobs on print queue");
529 static bool test_netprintdestenum(struct torture_context *tctx,
530 struct smbcli_state *cli)
532 struct rap_NetPrintDestEnum r;
534 uint16_t levels[] = { 0, 1, 2, 3 };
536 for (i=0; i < ARRAY_SIZE(levels); i++) {
538 r.in.level = levels[i];
541 torture_comment(tctx,
542 "Testing rap_NetPrintDestEnum level %d\n", r.in.level);
544 torture_assert_ntstatus_ok(tctx,
545 smbcli_rap_netprintdestenum(cli->tree, tctx, &r),
546 "smbcli_rap_netprintdestenum failed");
552 static bool test_netprintdestgetinfo_bydest(struct torture_context *tctx,
553 struct smbcli_state *cli,
554 const char *PrintDestName)
556 struct rap_NetPrintDestGetInfo r;
558 uint16_t levels[] = { 0, 1, 2, 3 };
560 for (i=0; i < ARRAY_SIZE(levels); i++) {
562 r.in.PrintDestName = PrintDestName;
563 r.in.level = levels[i];
566 torture_comment(tctx,
567 "Testing rap_NetPrintDestGetInfo(%s) level %d\n", r.in.PrintDestName, r.in.level);
569 torture_assert_ntstatus_ok(tctx,
570 smbcli_rap_netprintdestgetinfo(cli->tree, tctx, &r),
571 "smbcli_rap_netprintdestgetinfo failed");
578 static bool test_netprintdestgetinfo(struct torture_context *tctx,
579 struct smbcli_state *cli)
581 struct rap_NetPrintDestEnum r;
587 torture_comment(tctx,
588 "Testing rap_NetPrintDestEnum level %d\n", r.in.level);
590 torture_assert_ntstatus_ok(tctx,
591 smbcli_rap_netprintdestenum(cli->tree, tctx, &r),
592 "smbcli_rap_netprintdestenum failed");
594 for (i=0; i < r.out.count; i++) {
597 test_netprintdestgetinfo_bydest(tctx, cli, r.out.info[i].info2.PrinterName),
598 "failed to get printdest info");
605 static bool test_rap_print(struct torture_context *tctx,
606 struct smbcli_state *cli)
608 struct rap_NetPrintQEnum r;
614 torture_assert_ntstatus_ok(tctx,
615 smbcli_rap_netprintqenum(cli->tree, tctx, &r),
616 "failed to enum printq");
617 torture_assert_werr_ok(tctx, W_ERROR(r.out.status),
618 "failed to enum printq");
620 for (i=0; i < r.out.count; i++) {
622 const char *printqname = r.out.info[i].info5.PrintQueueName;
623 struct smbcli_tree *res_queue = NULL;
625 union rap_printj_info *job_info;
629 test_netprintq_pause(tctx, cli, printqname),
630 "failed to set printjobs on print queue");
632 torture_assert_ntstatus_ok(tctx,
633 torture_second_tcon(tctx, cli->session, printqname, &res_queue),
634 "failed to open 2nd connection");
637 print_printjob(tctx, res_queue),
638 "failed to print job on 2nd connection");
640 talloc_free(res_queue);
643 test_netprintjobenum_args(tctx, cli, printqname, 1,
644 &num_jobs, &job_info),
645 "failed to enum printjobs on print queue");
647 for (j=0; j < num_jobs; j++) {
649 uint16_t job_id = job_info[j].info1.JobID;
652 test_netprintjobgetinfo_byid(tctx, cli, job_id),
653 "failed to getinfo on new printjob");
656 test_netprintjob_delete(tctx, cli, job_id),
657 "failed to delete job");
661 test_netprintq_resume(tctx, cli, printqname),
662 "failed to resume print queue");
669 struct torture_suite *torture_rap_printing(TALLOC_CTX *mem_ctx)
671 struct torture_suite *suite = torture_suite_create(mem_ctx, "PRINTING");
673 torture_suite_add_1smb_test(suite, "raw_print", test_raw_print);
674 torture_suite_add_1smb_test(suite, "rap_print", test_rap_print);
675 torture_suite_add_1smb_test(suite, "rap_printq_enum", test_netprintqenum);
676 torture_suite_add_1smb_test(suite, "rap_printq_getinfo", test_netprintqgetinfo);
677 torture_suite_add_1smb_test(suite, "rap_printq", test_netprintq);
678 torture_suite_add_1smb_test(suite, "rap_printjob_enum", test_netprintjobenum);
679 torture_suite_add_1smb_test(suite, "rap_printjob_getinfo", test_netprintjobgetinfo);
680 torture_suite_add_1smb_test(suite, "rap_printjob_setinfo", test_netprintjobsetinfo);
681 torture_suite_add_1smb_test(suite, "rap_printjob", test_netprintjob);
682 torture_suite_add_1smb_test(suite, "rap_printdest_enum", test_netprintdestenum);
683 torture_suite_add_1smb_test(suite, "rap_printdest_getinfo", test_netprintdestgetinfo);